@@ -216,3 +216,127 @@ function countCountable(CountableFoo $x, int $mode)
216
216
}
217
217
assertType ('ListCount\CountableFoo ' , $ x );
218
218
}
219
+
220
+ class CountWithOptionalKeys
221
+ {
222
+ /**
223
+ * @param array{0: mixed, 1?: string|null} $row
224
+ */
225
+ protected function testOptionalKeys ($ row ): void
226
+ {
227
+ if (count ($ row ) === 0 ) {
228
+ assertType ('*NEVER* ' , $ row );
229
+ } else {
230
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
231
+ }
232
+
233
+ if (count ($ row ) === 1 ) {
234
+ assertType ('array{mixed} ' , $ row );
235
+ } else {
236
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
237
+ }
238
+
239
+ if (count ($ row ) === 2 ) {
240
+ assertType ('array{mixed, string|null} ' , $ row );
241
+ } else {
242
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
243
+ }
244
+
245
+ if (count ($ row ) === 3 ) {
246
+ assertType ('*NEVER* ' , $ row );
247
+ } else {
248
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
249
+ }
250
+ }
251
+
252
+ /**
253
+ * @param array{mixed}|array{0: mixed, 1?: string|null} $row
254
+ */
255
+ protected function testOptionalKeysInUnion ($ row ): void
256
+ {
257
+ if (count ($ row ) === 0 ) {
258
+ assertType ('*NEVER* ' , $ row );
259
+ } else {
260
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
261
+ }
262
+
263
+ if (count ($ row ) === 1 ) {
264
+ assertType ('array{mixed} ' , $ row );
265
+ } else {
266
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
267
+ }
268
+
269
+ if (count ($ row ) === 2 ) {
270
+ assertType ('array{mixed, string|null} ' , $ row );
271
+ } else {
272
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
273
+ }
274
+
275
+ if (count ($ row ) === 3 ) {
276
+ assertType ('*NEVER* ' , $ row );
277
+ } else {
278
+ assertType ('array{0: mixed, 1?: string|null} ' , $ row );
279
+ }
280
+ }
281
+
282
+ /**
283
+ * @param array{string}|array{0: int, 1?: string|null} $row
284
+ */
285
+ protected function testOptionalKeysInListsOfTaggedUnion ($ row ): void
286
+ {
287
+ if (count ($ row ) === 0 ) {
288
+ assertType ('*NEVER* ' , $ row );
289
+ } else {
290
+ assertType ('array{0: int, 1?: string|null}|array{string} ' , $ row );
291
+ }
292
+
293
+ if (count ($ row ) === 1 ) {
294
+ assertType ('array{0: int, 1?: string|null}|array{string} ' , $ row );
295
+ } else {
296
+ assertType ('array{0: int, 1?: string|null} ' , $ row );
297
+ }
298
+
299
+ if (count ($ row ) === 2 ) {
300
+ assertType ('array{int, string|null} ' , $ row );
301
+ } else {
302
+ assertType ('array{0: int, 1?: string|null}|array{string} ' , $ row );
303
+ }
304
+
305
+ if (count ($ row ) === 3 ) {
306
+ assertType ('*NEVER* ' , $ row );
307
+ } else {
308
+ assertType ('array{0: int, 1?: string|null}|array{string} ' , $ row );
309
+ }
310
+ }
311
+
312
+ /**
313
+ * @param array{string}|array{0: int, 3?: string|null} $row
314
+ */
315
+ protected function testOptionalKeysInUnionArray ($ row ): void
316
+ {
317
+ if (count ($ row ) === 0 ) {
318
+ assertType ('*NEVER* ' , $ row );
319
+ } else {
320
+ assertType ('array{0: int, 3?: string|null}|array{string} ' , $ row );
321
+ }
322
+
323
+ if (count ($ row ) === 1 ) {
324
+ assertType ('array{0: int, 3?: string|null}|array{string} ' , $ row );
325
+ } else {
326
+ assertType ('array{0: int, 3?: string|null} ' , $ row );
327
+ }
328
+
329
+ if (count ($ row ) === 2 ) {
330
+ assertType ('array{0: int, 3?: string|null} ' , $ row );
331
+ } else {
332
+ assertType ('array{0: int, 3?: string|null}|array{string} ' , $ row );
333
+ }
334
+
335
+ if (count ($ row ) === 3 ) {
336
+ assertType ('*NEVER* ' , $ row );
337
+ } else {
338
+ assertType ('array{0: int, 3?: string|null}|array{string} ' , $ row );
339
+ }
340
+ }
341
+
342
+ }
0 commit comments