1/*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16let arr = Array.from("abcd");
17print(arr);
18arr = Array.from("abcd");
19print(arr);
20arr[1] = 'e';
21print(arr);
22arr = Array.from("abcd");
23print(arr);
24
25arr = Array.from("01234567890123456789012");
26print(arr)
27arr = Array.from("方舟")
28print(arr);
29arr = Array.from("方舟")
30print(arr);
31arr = Array.from("")
32print(arr.length)
33arr[0] = 'a'
34arr = Array.from("")
35print(arr.length)
36
37var src = new Uint8Array(10000);
38for(var i = 0; i < 10000; i++)
39{
40    src[i] = 1;
41}
42arr = Array.from(src);
43print(arr[666]);
44print(arr[999]);
45print(arr.length);
46
47const v1 = new Map();
48print(Array.from(v1.keys()))
49
50{
51    let mp=new Map();
52    let mpIter = mp.entries();
53    mpIter.__proto__=[1,2,3,4];
54    let res=Array.from(mpIter);
55    print(res);
56}
57
58{
59    class MyArray1 extends Array {
60        constructor(...args) {
61            super(...args);
62            return {};
63        }
64    }
65    let arr1 = MyArray1.from([1,2,3,4]);
66    print(JSON.stringify(arr1));
67
68    class MyArray2 extends Array {
69        constructor(...args) {
70            super(...args);
71            return new Proxy({}, {
72                get(o, k) {
73                    print("get",k);
74                    return o[k];
75                 },
76                set(o, k, v) {
77                    print("set",k);
78                    return o[k]=v;
79                },
80                defineProperty(o, k, v) {
81                    print("defineProperty",k);
82                    return Object.defineProperty(o,k,v);
83                 }
84            });
85        }
86    }
87    let arr2 = MyArray2.from([1,2,3,4]);
88    print(JSON.stringify(arr2));
89
90    class MyArray3 extends Array {
91        constructor(...args) {
92            super(...args);
93            return new Proxy(this, {
94                get(o, k) {
95                    print("get",k);
96                    return o[k];
97                 },
98                set(o, k, v) {
99                    print("set",k);
100                    return o[k]=v;
101                },
102                defineProperty(o, k, v) {
103                    print("defineProperty",k);
104                    return Object.defineProperty(o,k,v);
105                 }
106            });
107        }
108    }
109    let arr3 = MyArray3.from([1,2,3,4]);
110    print(JSON.stringify(arr3));
111}
112
113{
114    let arrIterBak = Array.prototype[Symbol.iterator];
115    let obj = {
116        get length() {
117            print("get length");
118            return 10;
119        },
120        set length(x) {
121            print("set length", x);
122            return true;
123        },
124        get 0() {
125            print('get 0');
126            return 0;
127        },
128        get 1() {
129            print('get 1');
130            return 1;
131        },
132        get 2() {
133            print('get 2');
134            return 2;
135        },
136        get [Symbol.iterator]() {
137            print("get iterator");
138            return arrIterBak;
139        }
140    }
141    let res = Array.from(obj);
142    print(JSON.stringify(res));
143}
144
145{
146    let arr = [1, 2, 3, 4, 5, 6];
147    Object.defineProperty(arr, 0, {
148        get() {
149            print("get 0");
150            arr.pop();
151            return "x";
152        }
153    });
154    let res = Array.from(arr);
155    print(JSON.stringify(res))
156}
157{
158    let arrIterBak = Array.prototype[Symbol.iterator];
159    let arr = new Object(1);
160    arr[1] = 1;
161    arr.length = 10;
162    arr[Symbol.iterator] = arrIterBak;
163    print(arr.constructor)
164    let res = Array.from(arr);
165    print(JSON.stringify(res))
166}
167{
168    let arrIterBak = Array.prototype[Symbol.iterator];
169    Number.prototype.__proto__ = {
170        get length() {
171            print("get length");
172            return 10;
173        },
174        set length(x) {
175            print("set length", x);
176            return true;
177        },
178        get 0() {
179            print('get 0');
180            return 0;
181        },
182        get 1() {
183            print('get 1');
184            return 1;
185        },
186        get 2() {
187            print('get 2');
188            return 2;
189        },
190        get [Symbol.iterator]() {
191            print("get iterator");
192            return arrIterBak;
193        }
194    };
195    let arr = 1
196    let res = Array.from(arr);
197    print(JSON.stringify(res))
198}
199
200{
201    let arr = [1,2,3];
202    let res = Array.from(arr.values());
203    print(JSON.stringify(res));
204}
205
206// array.from by arrayLike with mapFunc
207{
208    let res = Array.from({length : 3}, () => {});
209    print(JSON.stringify(res));
210}
211
212{
213    let res = Array.from({length : 3}, () => ({}));
214    print(JSON.stringify(res));
215}
216
217{
218    let res = Array.from({length : 3}, () => []);
219    print(JSON.stringify(res));
220}
221
222{
223    let res = Array.from({length : 3}, () => [1,2,3]);
224    print(JSON.stringify(res));
225}
226
227{
228    let res = Array.from({length : 3}, () => 0);
229    print(JSON.stringify(res));
230}
231
232{
233    let num = 1;
234    let len = 1025;
235    let res = Array.from({length : len}, () => num);
236    print(res.length == len);
237    let flag = true;
238    for (let i = 0; i < res.length; ++i) {
239      if (res[i] != num) {
240        flag = false;
241        break;
242      }
243    }
244    if (flag) {
245      print("get JSArray from arrayLike Success");
246    }
247}
248
249{
250    function example() {
251      let res = Array.from(arguments);
252      print(JSON.stringify(res));
253    }
254    example(1, 2, 3);
255}
256
257{
258    let arrayLike = {0:1.1, 1:12, 2:'ss', length: 3}
259    let res = Array.from(arrayLike, x => x + x);
260    print(JSON.stringify(res));
261}
262
263{
264    let res = Array.from({length : 3}, (_, index) => [index * 2]);
265    print(JSON.stringify(res));
266}
267
268{
269    const nonConstructor = {}
270    let res = Array.from.call(nonConstructor, {length : 3}, (_, index) => [index * 2]);
271    print(JSON.stringify(res));
272}
273
274//array.from by JSArray
275{
276    const nonConstructor = {}
277    let num = 1
278    let len = 1025 // may transfer to dictionary elements type
279    let myArray = new Array(1025).fill(num)
280    let res = Array.from.call(nonConstructor, myArray);
281    print(res.length == len);
282    let flag = true;
283    for (let i = 0; i < res.length; ++i) {
284      if (res[i] != num || res.at(i) != num) {
285        flag = false;
286        break;
287      }
288    }
289    if (flag) {
290      print("get JSArray from JSArray Success!")
291    }
292}
293
294{
295    const nonConstructor = {}
296    let myArray = new Array(1,2,3,4,5)
297    let res = Array.from.call(nonConstructor, myArray);
298    print(JSON.stringify(res));
299}
300
301{
302    let res = Array.from([1,2,3,4,5]);
303    print(JSON.stringify(res));
304}
305
306// test for String with mapFunc
307{
308    let str = 'a'.repeat(10)
309    let res = Array.from(str, x => x + 's');
310    print(JSON.stringify(res));
311}
312
313{
314    let len = 1025
315    const head = 'h'
316    const tail = '_tail'
317    let str = head.repeat(len)
318    let res = Array.from(str, x => x + tail);
319    let flag = true;
320    for (let i = 0; i < res.length; ++i) {
321      if (res[i] != head + tail) {
322        flag = false;
323        break;
324      }
325    }
326    if (res.length == len && flag) {
327      print("result check successfully");
328    } else {
329      print("result check failed");
330    }
331}
332
333// test for Set with mapFunc
334{
335    let set = new Set(['test', 'for', 'array', 'from', 'set'])
336    let res = Array.from(set, x => x);
337    print(JSON.stringify(res));
338}
339
340// test for Map with mapFunc
341{
342    let map = new Map([[1, 'test'], [2, 'for'], [3, 'array'], [4, 'from'], [5, 'map']]);
343    let res = Array.from(map, x => x);
344    print(JSON.stringify(res));
345}
346
347// test for TypedArray with mapFunc
348{
349    let mapFunc = x => x + x;
350    let uint8Array = new Uint8Array([1, 2, 3, 4, 5, 6]);
351    let res = Array.from(uint8Array, mapFunc);
352    print(JSON.stringify(res));
353}
354
355{
356    let mapFunc = x => x + x;
357    let uint16Array = new Uint16Array([1, 2, 3, 4, 5, 6]);
358    let res = Array.from(uint16Array, mapFunc);
359    print(JSON.stringify(res));
360}
361
362{
363    let mapFunc = x => x + x;
364    let uint32Array = new Uint32Array([1, 2, 3, 4, 5, 6]);
365    let res = Array.from(uint32Array, mapFunc);
366    print(JSON.stringify(res));
367}
368
369{
370    let mapFunc = x => x + x;
371    let float32Array = new Float32Array([1, 2, 3, 4, 5, 6]);
372    let res = Array.from(float32Array, mapFunc);
373    print(JSON.stringify(res));
374}
375
376{
377    let mapFunc = x => x + x;
378    let float64Array = new Float64Array([1, 2, 3, 4, 5, 6]);
379    let res = Array.from(float64Array, mapFunc);
380    print(JSON.stringify(res));
381}