Skip to content

Commit 88a64f5

Browse files
committed
Add F::data(List<T>) function & expand tests.
1 parent 29b4718 commit 88a64f5

File tree

3 files changed

+66
-7
lines changed

3 files changed

+66
-7
lines changed

examples/test.cpp

Lines changed: 24 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -136,13 +136,6 @@ PURE String show(LIST<T> xs)
136136
return str;
137137
}
138138

139-
template <typename T>
140-
void TEST_FIND_ALL(T xs)
141-
{
142-
for (auto x: xs)
143-
TEST(!empty(find(xs, x)));
144-
}
145-
146139
/****************************************************************************/
147140

148141
int main(void)
@@ -152,37 +145,56 @@ int main(void)
152145
auto xs = list<int>();
153146
for (int i = 30; i >= 0; i--)
154147
xs = list(i, xs);
148+
const double data[] = {-1.1, 10.0, 3.222, -55.0, 3.2, 2.2, 0.00001};
149+
auto ys = list<double>();
150+
for (int i = sizeof(data) / sizeof(data[0]) - 1; i >= 0; i--)
151+
ys = list(data[i], ys);
155152

156153
printf("\n\33[33mxs = %s\33[0m\n", c_str(show(xs)));
154+
printf("\n\33[33mys = %s\33[0m\n", c_str(show(ys)));
157155
TEST(index(list<int>()) == 0);
158156
TEST(size(list<int>()) == 0);
159157
TEST(empty(list<int>()));
160158
TEST(index(xs) == 1);
159+
TEST(index(ys) == 1);
161160
TEST(!empty(xs));
161+
TEST(!empty(ys));
162162
TEST(size(xs) == 31);
163+
TEST(size(ys) == sizeof(data) / sizeof(data[0]));
163164
TEST(head(xs) == 0);
165+
TEST(head(ys) == -1.1);
164166
TEST(size(tail(xs)) == 30);
165167
TEST(head(tail(xs)) == 1);
168+
TEST(head(tail(ys)) == 10.0);
166169
TEST(last(xs) == 30);
170+
TEST(last(ys) == 0.00001);
167171
TEST(size(take(xs, 2)) == 2);
168172
TEST(head(take(xs, 2)) == 0);
169173
TEST(last(take(xs, 2)) == 1);
174+
TEST(memcmp(F::data(ys), data, sizeof(data)) == 0);
170175
TEST(size(take_while(xs, [] (int x) { return x <= 2; })) == 3);
171176
TEST(last(take_while(xs, [] (int x) { return x <= 2; })) == 2);
172177
TEST(size(append(xs, xs)) == 62);
173178
TEST(last(append(xs, xs)) == last(xs));
174179
TEST(head(reverse(xs)) == last(xs));
175180
TEST(second(head(zip(xs, xs))) == head(xs));
176181
TEST(first(last(zip(xs, xs))) == last(xs));
182+
TEST(second(head(zip(ys, xs))) == head(xs));
183+
TEST(first(last(zip(ys, xs))) == last(ys));
177184
TEST(compare(sort(xs), xs) == 0);
185+
TEST(head(sort(ys)) == -55.0);
186+
TEST(last(sort(ys)) == 10.0);
178187
TEST(compare(sort(xs, [] (int x, int y) { return y-x; }),
179188
reverse(xs)) == 0);
180189
TEST(foldl(xs, true, [] (bool a, int x) { return (a && (x <= 30)); }));
181190
TEST(foldl(xs, 0, [] (int x, int y) { return x+y; }) == 465);
182191
TEST(foldl(xs, 0, [] (int x, int y) { return y; }) == 30);
192+
TEST(foldl(ys, 100000.0, [] (double a, double x) { return (x < a? x: a); }) == -55.0);
183193
TEST(foldr(xs, 0, [] (int x, int y) { return y; }) == 0);
194+
TEST(foldr(ys, 100000.0, [] (double a, double x) { return (x < a? x: a); }) == -55.0);
184195
TEST(({int sum = 0; for (int x: xs) sum += x; sum;}) == 465);
185196
TEST(last(map<int>(xs, [] (int x) { return x+1; })) == 31);
197+
TEST(compare(map<int>(ys, [] (double x) { return (int)x; }), xs) != 0);
186198
TEST(size(filter(xs, [] (int x) { return x != 1 && x != 2; })) == 29);
187199
TEST(compare(xs, xs) == 0);
188200
TEST(compare(xs, tail(xs)) < 0);
@@ -211,6 +223,7 @@ int main(void)
211223
TEST(compare(string('X'), string("X")) == 0);
212224
TEST(size(str) == 76);
213225
TEST(size(append(str, str)) == 2 * size(str));
226+
TEST(compare(string(c_str(str)), str) == 0);
214227
TEST(lookup(append(str, 'X'), 76) == 'X');
215228
TEST(lookup(append(str, "ABC123"), 76+3) == '1');
216229
TEST(size((str + str)) == 2 * size(str));
@@ -320,6 +333,10 @@ int main(void)
320333
TEST(verify(ws));
321334
TEST(memcmp(F::data(ws), data, sizeof(data)) == 0);
322335
TEST(memcmp(F::data(ws), F::data(xs), sizeof(data)) != 0);
336+
TEST(compare(vector(F::data(xs), size(xs)), xs) == 0);
337+
TEST(compare(vector(F::data(ys), size(ys)), ys) == 0);
338+
TEST(compare(vector(F::data(zs), size(zs)), zs) == 0);
339+
TEST(compare(vector(F::data(ws), size(ws)), ws) == 0);
323340
TEST(size(xs) == 300);
324341
TEST(size(ys) == size(string("Hello World!")));
325342
TEST(size(zs) == 3);

flist.cpp

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,28 @@
4040
namespace F
4141
{
4242

43+
/*
44+
* Covert to C-array.
45+
*/
46+
extern PURE void *_list_data(List<Word> xs, size_t size,
47+
void (*copy)(void *, Value<Word>))
48+
{
49+
size_t len = _list_length(xs);
50+
if (len == 0)
51+
return nullptr;
52+
void *ptr0 = (size < sizeof(void *)?
53+
gc_malloc_atomic(len * size): gc_malloc(len * size));
54+
uint8_t *ptr = (uint8_t *)ptr0;
55+
while (!empty(xs))
56+
{
57+
const Node<Word> &node = xs;
58+
copy(ptr, node.elem);
59+
ptr += size;
60+
xs = tail(xs);
61+
}
62+
return ptr0;
63+
}
64+
4365
/*
4466
* Last.
4567
*/

flist.h

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,8 @@ extern PURE List<char32_t> _string_list(_Seq s);
5555
/*
5656
* Low-level implementation.
5757
*/
58+
extern PURE void *_list_data(List<Word> _xs, size_t _size,
59+
void (*_copy)(void *, Value<Word>));
5860
extern PURE List<Word> _list_last(List<Word> _xs);
5961
extern PURE size_t _list_length(List<Word> _xs);
6062
extern PURE List<Word> _list_append(List<Word> _xs, List<Word> _ys);
@@ -142,6 +144,24 @@ inline PURE List<char32_t> list(String _s)
142144
return _string_list(_s._impl);
143145
}
144146

147+
/**
148+
* Convert a list into a C-array.
149+
* O(n).
150+
*/
151+
template <typename _T>
152+
inline PURE const _T *data(List<_T> _xs)
153+
{
154+
void (*_copy)(void *, Value<Word>) =
155+
[](void *_ptr, Value<Word> _elem0)
156+
{
157+
Value<_T> _elem1 = _bit_cast<Value<_T>>(_elem0);
158+
const _T &_elem = _elem1;
159+
*(_T *)_ptr = _elem;
160+
};
161+
return (const _T *)_list_data(_bit_cast<List<Word>>(_xs), sizeof(_T),
162+
_copy);
163+
}
164+
145165
/**
146166
* Test if a list is empty.
147167
* O(1).

0 commit comments

Comments
 (0)