1 // RUNNABLE_PHOBOS_TEST
2 // PERMUTE_ARGS:
3 
4 extern(C) int printf(const char*, ...);
5 
6 /************************************************/
7 
8 int a[string];
9 
foo(immutable char[3]s)10 size_t foo(immutable char [3] s)
11 {
12     printf("foo()\n");
13     int b[string];
14     string[] key;
15     int[] value;
16     printf("foo() 2\n");
17     key = a.keys;
18     printf("foo() 3\n");
19     value = a.values;
20     printf("foo() 4\n");
21     return a.length + b.length;
22 }
23 
foo2()24 void foo2()
25 {
26     int c[string];
27     string[] key;
28     int[] value;
29     int i;
30 
31     assert(c.length == 0);
32     key = c.keys;
33     assert(key.length == 0);
34     value = c.values;
35     assert(value.length == 0);
36 
37     c["foo"] = 3;
38     assert(c["foo"] == 3);
39     assert(c.length == 1);
40     key = c.keys;
41     assert(key.length == 1);
42     value = c.values;
43     assert(value.length == 1);
44     assert(value[0] == 3);
45 
46     c["bar"] = 4;
47     assert(c["bar"] == 4);
48     assert(c.length == 2);
49     key = c.keys;
50     assert(key.length == 2);
51     value = c.values;
52     assert(value.length == 2);
53 
54     for (i = 0; i < key.length; i++)
55     {
56         printf("c[\"%.*s\"] = %d\n", key[i].length, key[i].ptr, value[i]);
57     }
58 
59     assert("foo" in c);
60     c.remove("foo");
61     assert(!("foo" in c));
62     assert(c.length == 1);
63 
64     assert("bar" in c);
65     c.remove("bar");
66     assert(!("bar" in c));
67     assert(c.length == 0);
68 }
69 
testaa()70 void testaa()
71 {
72     size_t i = foo("abc");
73     printf("i = %d\n", i);
74     assert(i == 0);
75 
76     foo2();
77 }
78 
79 /************************************************/
80 
test1899()81 void test1899()
82 {
83     int[3][string] AA;
84     int[3] x = [5,4,3];
85     AA["abc"] = x;
86     assert(AA["abc"] == x);
87     AA["def"] = [1,2,3];
88     assert(AA["def"]==[1,2,3]);
89 }
90 
91 /************************************************/
92 
foo4523()93 void foo4523()
94 {
95    int[string] aa = ["test":0, "test2":1];
96 
97    bool found = aa.remove("test");
98    assert(found);
99    bool notfound = aa.remove("nothing");
100    assert(!notfound);
101 }
102 
test4523()103 void test4523()
104 {
105     foo4523();
106     static assert({ foo4523(); return true; }());
107 }
108 
109 /************************************************/
110 // 3825
111 
112 import std.math;    // necessary for ^^=
test3825()113 void test3825()
114 {
115     // Check for RangeError is thrown
116     bool thrown(T)(lazy T cond)
117     {
118         import core.exception;
119         bool f = false;
120         try {
121             cond();
122         } catch (RangeError e) { f = true; }
123         return f;
124     }
125 
126     int[int] aax;
127     int[][int] aay;
128 
129     aax = null, aay = null;
130     assert(thrown(aax[0]));
131     assert(thrown(aax[0]   = aax[0]));  // rhs throws
132     assert(thrown(aax[0]  += aax[0]));  // rhs throws
133     assert(thrown(aax[0] ^^= aax[0]));  // rhs throws
134     assert(thrown(aay[0]  ~= aay[0]));  // rhs throws
135     aax = null;   aax[0]   = 1;  assert(aax[0] ==  1);  // setting aax[0] is OK
136     aax = null;   aax[0]  += 1;  assert(aax[0] == +1);  // setting aax[0] to 0 and modify it is OK
137     aax = null;   aax[0] ^^= 1;  assert(aax[0] ==  0);  // setting aax[0] to 0 and modify it is OK
138     aay = null;   aay[0]  ~= []; assert(aay[0] == []);  // setting aay[0] to 0 and modify it is OK
139     aax = null; ++aax[0];        assert(aax[0] == +1);  // setting aax[0] to 0 and modify it is OK
140     aax = null; --aax[0];        assert(aax[0] == -1);  // setting aax[0] to 0 and modify it is OK
141 
142     aax = [0:0], aay = [0:null];
143     assert(thrown(aax[aax[1]]   = 1));  // accessing aax[1] in key part throws
144     assert(thrown(aax[aax[1]]  += 1));  // accessing aax[1] in key part throws
145     assert(thrown(aax[aax[1]] ^^= 1));  // accessing aax[1] in key part throws
146     assert(thrown(aay[aax[1]]  ~= [])); // accessing aax[1] in key part throws
147 
148     //assert(thrown(aax[(  aax[1], 0)] = 0));
149     /* accessing aax[1] in key part, why doesn't throw?
150      * Because, in aax[(aax[1], 0)], aax[1] is in lhs of comma expression, and is treated
151      * it has no side effect. Then optimizer eliminate it completely, and
152      * whole expression succeed to run in runtime. */
153     int n = 0;
154     assert(thrown(aax[((){ n=aax[1]; return 0;}())] = 0)); // accessing aax[1] in key part, throws OK
155 
156     // This works as expected.
157     int[int][int] aaa;
158     aaa[0][0] = 0;              assert(aaa[0][0] == 0); // setting aaa[0][0] is OK
159 
160     // real test cases
161     void bug3825()
162     {
163         string[] words = ["how", "are", "you", "are"];
164 
165         int[string] aa1;
166         foreach (w; words)
167             aa1[w] = ((w in aa1) ? (aa1[w] + 1) : 2);
168         //writeln(aa1); // Prints: [how:1,you:1,are:2]
169 
170         int[string] aa2;
171         foreach (w; words)
172             if (w in aa2)
173                 aa2[w]++;
174             else
175                 aa2[w] = 2;
176         //writeln(aa2); // Prints: [how:2,you:2,are:3]
177 
178         assert(aa1 == aa2);
179         assert(aa1 == ["how":2, "you":2, "are":3]);
180         assert(aa2 == ["how":2, "you":2, "are":3]);
181     }
182     void bug5021()
183     {
184         int func()
185         {
186             throw new Exception("It's an exception.");
187         }
188 
189         int[string] arr;
190         try
191         {
192             arr["hello"] = func();
193         }
194         catch(Exception e)
195         {
196         }
197         assert(arr.length == 0);
198     }
199     void bug7914()
200     {
201         size_t[ubyte] aa;
202         aa[0] = aa.length;
203         assert(aa[0] == 0);
204     }
205     void bug8070()
206     {
207         Object[string] arr;
208 
209         class A
210         {
211             this()
212             {
213                 // at this point:
214                 assert("x" !in arr);
215             }
216         }
217 
218         arr["x"] = new A();
219     }
220     bug3825();
221     bug5021();
222     bug7914();
223     bug8070();
224 }
225 
test3825x()226 void test3825x()
227 {
228     return; // depends on AA implementation
229     static int ctor, cpctor, dtor;
230 
231     static struct S
232     {
233         this(int)  { ++ctor; }
234         this(this) { ++cpctor; }
235         ~this()    { ++dtor; }
236     }
237 
238     int[S] aa;
239     {
240         auto value = S(1);
241         assert(ctor==1 && cpctor==0 && dtor==0);
242 
243         ref getRef(ref S s = value) { return s; }
244         auto getVal() { return value; }
245 
246         aa[value] = 10;
247         assert(ctor==1 && cpctor==1 && dtor==0);
248 
249         aa[getRef()] += 1;
250         assert(ctor==1 && cpctor==1 && dtor==0);
251 
252         aa[getVal()] += 1;
253         assert(ctor==1 && cpctor==2 && dtor==1);
254     }
255     assert(ctor==1 && cpctor==2 && dtor==2);
256     assert(ctor + cpctor - aa.length == dtor);
257 }
258 
259 /************************************************/
260 // 10106
261 
262 struct GcPolicy10106 {}
263 
264 struct Uint24Array10106(SP = GcPolicy10106)
265 {
this(this)266     this(this) {}
267 }
268 
269 struct InversionList10106(SP = GcPolicy10106)
270 {
271     Uint24Array10106!SP data;
272 }
273 
274 alias InversionList10106!GcPolicy10106 CodepointSet10106;
275 
276 struct PropertyTable10106
277 {
278     CodepointSet10106[string] table;
279 }
280 
281 /************************************************/
282 
main()283 int main()
284 {
285     testaa();
286     test1899();
287     test4523();
288     test3825();
289     test3825x();
290 
291     printf("Success\n");
292     return 0;
293 }
294