refactored list.crossproduct() to avoid JS stack overflows

pull/95/head
jmoenig 2021-02-09 00:58:26 +01:00
rodzic 81ad8de5d7
commit 1b72285310
3 zmienionych plików z 28 dodań i 11 usunięć

Wyświetl plik

@ -9,7 +9,10 @@
* **Documentation Updates:**
* updated manual (e.g. p.20) with hyper-semantics of ITEM OF, thanks Brian
### 2021-02-06
### 2021-02-09
* lists: refactored matrix ops to avoid JS stack overflows
### 2021-02-08
* lists, objects, threads: new RESHAPE primitive
* lists: added internal naive (recursive) version of CROSSPRODUCT
* lists: added TRANSPOSE for higher dimensions, thanks, Brian!

Wyświetl plik

@ -9,7 +9,7 @@
<script src="src/symbols.js?version=2020-10-07"></script>
<script src="src/widgets.js?version=2021-01-05"></script>
<script src="src/blocks.js?version=2021-02-08"></script>
<script src="src/threads.js?version=2021-02-08"></script>
<script src="src/threads.js?version=2021-02-09"></script>
<script src="src/objects.js?version=2021-02-08"></script>
<script src="src/gui.js?version=2021-02-04"></script>
<script src="src/paint.js?version=2020-05-17"></script>

Wyświetl plik

@ -63,7 +63,7 @@ MorphicPreferences, TableDialogMorph, SpriteBubbleMorph, SpeechBubbleMorph,
TableFrameMorph, TableMorph, Variable, isSnapObject, Costume, contains, detect,
ZERO, WHITE*/
modules.lists = '2021-February-08';
modules.lists = '2021-February-09';
var List;
var ListWatcherMorph;
@ -544,7 +544,8 @@ List.prototype.getDimension = function (rank = 0) {
};
List.prototype.width = function () {
// private - answer the maximum length of my direct sub-lists (columns), if any
// private - answer the maximum length of my direct sub-lists (columns),
// if any
var i, item,
width = 0,
len = this.length();
@ -660,14 +661,27 @@ List.prototype.crossproduct = function () {
// expects myself to be a list of lists.
// answers a new list of all possible tuples
// with one item from each of my sublists
if (this.isEmpty()) {
return new List([new List()]);
var result = new List(),
len = this.length(),
lengths = this.map(each => each.length()),
size = lengths.itemsArray().reduce((a, b) => a * b),
i, k, row, factor;
for (i = 1; i <= size; i += 1) {
row = new List();
factor = 1;
for (k = 1; k <= len; k += 1) {
row.add(
this.at(k).at(
((Math.ceil(i / ((size / lengths.at(k)) * factor)) - 1) %
lengths.at(k)) + 1
)
);
factor /= lengths.at(k);
}
result.add(row);
}
return this.at(1).map(
first => this.cdr().crossproduct().map(
each => this.cons(first, each)
)
).flatten();
return result;
};
List.prototype.strideTranspose = function () {