diff --git a/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t01.dart b/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t01.dart index 33516d280b..c15b56290d 100644 --- a/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t01.dart +++ b/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t01.dart @@ -9,9 +9,9 @@ /// declaration S when looked up on D. /// ... /// - An expression of the form `.` is a constant expression if S -/// declares a constant getter. +/// declares a corresponding static constant getter. /// -/// @description Checks that expressions of the form `'.' ` is a +/// @description Checks that an expression of the form `'.' ` is a /// constant expression if the appropriate declaration declares a constant /// getter with the name ``. /// @author sgrekhov22@gmail.com diff --git a/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t02.dart b/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t02.dart index c40988e628..825a9d4877 100644 --- a/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t02.dart +++ b/LanguageFeatures/Static-access-shorthand/constant_expression_A02_t02.dart @@ -9,34 +9,50 @@ /// declaration S when looked up on D. /// ... /// - An expression of the form `.` is a constant expression if S -/// declares a constant getter. +/// declares a corresponding static constant getter. /// -/// @description Checks that it is a compile-time error to use an expressions of +/// @description Checks that it is a compile-time error to use an expression of /// the form `'.' ` in a constant context if `` is an -/// explicit getter declaration. +/// explicit or implicit non-constant getter declaration. /// @author sgrekhov22@gmail.com // SharedOptions=--enable-experiment=enum-shorthands class C { final String value; - static C get instance => const C("C instance"); + static C get instance1 => const C("C instance1"); + static final C instance2 = const C("C instance2"); const C(this.value); } extension type const ET(String value) { - static ET get instance => const ET("ET instance"); + static ET get instance1 => const ET("ET instance1"); + static final ET instance2 = const ET("ET instance2"); } main() { - const C c = .instance; -// ^ + C nc1 = .instance1; // Ok + const C c1 = .instance1; +// ^ // [analyzer] unspecified // [cfe] unspecified - const ET et = .instance; -// ^ + C nc2 = .instance2; + const C c2 = .instance2; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + + ET net1 = .instance1; + const ET et1 = .instance1; +// ^ +// [analyzer] unspecified +// [cfe] unspecified + + ET net2 = .instance2; + const ET et2 = .instance2; +// ^ // [analyzer] unspecified // [cfe] unspecified } diff --git a/LanguageFeatures/Static-access-shorthand/constant_expression_A07_t01.dart b/LanguageFeatures/Static-access-shorthand/constant_expression_A07_t01.dart index 48e13b9477..623be9e78d 100644 --- a/LanguageFeatures/Static-access-shorthand/constant_expression_A07_t01.dart +++ b/LanguageFeatures/Static-access-shorthand/constant_expression_A07_t01.dart @@ -10,9 +10,10 @@ /// ... /// - An expression of `.id(arguments)` or `.new(arguments)` is a constant /// expression if (and only if) it occurs in a constant context, S declares a -/// constant constructor, every expression in arguments (which then occurs in -/// a constant context too) is a constant expression, and inferred type -/// arguments, if any, are all constant types. +/// corresponding constant constructor, every expression in `arguments` (which +/// then occurs in a constant context too) is a constant expression, and +/// inferred type arguments to the target class, if any, are all constant +/// types. /// /// @description Checks that an expression of the form `'.' id(arguments)` or /// `'.' new(arguments)` is not a constant expression if inferred type arguments diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t01.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t01.dart index a36dbf7821..44cb8f1f56 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t01.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t01.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t02.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t02.dart index 079109cffa..7e55fab4a5 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t02.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t02.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t03.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t03.dart index 814f8ff3f8..2ebae07c4d 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t03.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t03.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t04.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t04.dart index fd12ed320e..2c3c01370b 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t04.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t04.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t05.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t05.dart index 063e4f3e24..f3439c0d6e 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t05.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t05.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t06.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t06.dart index 8531d8615b..f762c12fa5 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t06.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t06.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t07.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t07.dart index aef91411f7..2a045736ab 100644 --- a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t07.dart +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t07.dart @@ -2,9 +2,8 @@ // for details. All rights reserved. Use of this source code is governed by a // BSD-style license that can be found in the LICENSE file. -/// @assertion Declaration denoted by a type scheme A context type scheme is -/// said to denote a declaration in some cases. Not all context type schemes -/// denote a declaration. +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. /// If a type scheme `S`: /// - has the form `C` or `C` where `C` is a type introduced by a /// declaration `D` which must therefore be a type-introducing declaration, diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t08.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t08.dart new file mode 100644 index 0000000000..734a0be1f3 --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t08.dart @@ -0,0 +1,67 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `C`, `C<...>`, `C?`, or `C<...>?` and `C` is a type introduced by the +/// type declaration `D`, then the shorthand context denotes the type +/// declaration `D`. Test a class. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import '../../Utils/expect.dart'; + +class C { + T value; + C(this.value); + C.id(this.value); + factory C.f(T t) = C; + + static C get staticGetter => C(4); + static C staticMethod(X x) => C(x); + static C instance = C("one"); +} + +main() { + C? c1 = .new(1); + Expect.equals(1, c1.value); + + C? c2 = .id(2); + Expect.equals(2, c2.value); + + C? c3 = .f(3); + Expect.equals(3, c3.value); + + C? c4 = .staticGetter; + Expect.equals(4, c4.value); + + C? c5 = .staticGetter; + Expect.equals(4, c5.value); + + C? c6 = .staticMethod(6); + Expect.equals(6, c6.value); + + C? c7 = .staticMethod(7); + Expect.equals(7, c7.value); + + C? c8 = .instance; + Expect.equals("one", c8.value); + + C? c9 = .instance; + Expect.equals("one", c9.value); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t09.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t09.dart new file mode 100644 index 0000000000..712a4b384b --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t09.dart @@ -0,0 +1,70 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `FutureOr`, `FutureOr>`, `FutureOr?`, +/// `FutureOr>?`, `FutureOr`, `FutureOr?>`, `FutureOr?` or +/// `FutureOr?>?` and `C` is a type introduced by the type declaration +/// `D`, then the shorthand context denotes the type declaration `D`. Test a +/// class. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import 'dart:async'; +import '../../Utils/expect.dart'; + +class C { + T value; + C(this.value); + C.id(this.value); + factory C.f(T t) = C; + + static C get staticGetter => C(4); + static C staticMethod(X x) => C(x); + static C instance = C("one"); +} + +main() async { + FutureOr? c1 = .new(1); + Expect.equals(1, (await c1)?.value); + + FutureOr? c2 = .id(2); + Expect.equals(2, (await c2)?.value); + + FutureOr?>? c3 = .f(3); + Expect.equals(3, (await c3)?.value); + + FutureOr?>? c4 = .staticGetter; + Expect.equals(4, (await c4)?.value); + + FutureOr? c5 = .staticGetter; + Expect.equals(4, (await c5)?.value); + + FutureOr?>? c6 = .staticMethod(6); + Expect.equals(6, (await c6)?.value); + + FutureOr? c7 = .staticMethod(7); + Expect.equals(7, (await c7)?.value); + + FutureOr?>? c8 = .instance; + Expect.equals("one", (await c8)?.value); + + FutureOr? c9 = .instance; + Expect.equals("one", (await c9)?.value); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t10.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t10.dart new file mode 100644 index 0000000000..fabcfcf2c0 --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t10.dart @@ -0,0 +1,68 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `C`, `C<...>`, `C?`, or `C<...>?` and `C` is a type introduced by the +/// type declaration `D`, then the shorthand context denotes the type +/// declaration `D`. Test a mixin. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import '../../Utils/expect.dart'; + +class C { + T value; + C(this.value); +} + +mixin M on C { + static M get staticGetter => MC(1); + static M staticMethod(X x) => MC(x); + static M instance = MC("one"); + + @override + bool operator ==(Object other) { + if (other is C) { + return value == other.value; + } + return false; + } +} + +class MC = C with M; + +main() { + M? m1 = .staticGetter; + Expect.equals(MC(1), m1); + + M? m2 = .staticGetter; + Expect.equals(MC(1), m2); + + M? m3 = .staticMethod(3); + Expect.equals(MC(3), m3); + + M? m4 = .staticMethod(4); + Expect.equals(MC(4), m4); + + M? m5 = .instance; + Expect.equals(MC("one"), m5); + + M? m6 = .instance; + Expect.equals(MC("one"), m6); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t11.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t11.dart new file mode 100644 index 0000000000..3abb67a4ec --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t11.dart @@ -0,0 +1,71 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `FutureOr`, `FutureOr>`, `FutureOr?`, +/// `FutureOr>?`, `FutureOr`, `FutureOr?>`, `FutureOr?` or +/// `FutureOr?>?` and `C` is a type introduced by the type declaration +/// `D`, then the shorthand context denotes the type declaration `D`. Test a +/// mixin. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import 'dart:async'; +import '../../Utils/expect.dart'; + +class C { + T value; + C(this.value); +} + +mixin M on C { + static M get staticGetter => MC(1); + static M staticMethod(X x) => MC(x); + static M instance = MC("one"); + + @override + bool operator ==(Object other) { + if (other is C) { + return value == other.value; + } + return false; + } +} + +class MC = C with M; + +main() async { + FutureOr?>? m1 = .staticGetter; + Expect.equals(MC(1), await m1); + + FutureOr? m2 = .staticGetter; + Expect.equals(MC(1), await m2); + + FutureOr?>? m3 = .staticMethod(3); + Expect.equals(MC(3), await m3); + + FutureOr? m4 = .staticMethod(4); + Expect.equals(MC(4), await m4); + + FutureOr?>? m5 = .instance; + Expect.equals(MC("one"), await m5); + + FutureOr? m6 = .instance; + Expect.equals(MC("one"), await m6); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t12.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t12.dart new file mode 100644 index 0000000000..863f7c8152 --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t12.dart @@ -0,0 +1,63 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `C`, `C<...>`, `C?`, or `C<...>?` and `C` is a type introduced by the +/// type declaration `D`, then the shorthand context denotes the type +/// declaration `D`. Test an enum. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import '../../Utils/expect.dart'; + +enum E { + e1(1), e2(2), e3("3"), e4("4"); + final T value; + const E(this.value); + + static E get staticGetter => E.e1; + static E staticMethod() => E.e2; + static E instance = E.e3; +} + +main() { + E? e1 = .staticGetter; + Expect.equals(E.e1, e1); + + E? e2 = .staticGetter; + Expect.equals(E.e1, e2); + + E? e3 = .staticMethod(); + Expect.equals(E.e2, e3); + + E? e4 = .staticMethod(); + Expect.equals(E.e2, e4); + + E? e5 = .instance; + Expect.equals(E.e3, e5); + + E? e6 = .instance; + Expect.equals(E.e3, e6); + + E? e7 = .e4; + Expect.equals(E.e4, e7); + + E? e8 = .e4; + Expect.equals(E.e4, e8); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t13.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t13.dart new file mode 100644 index 0000000000..39a309d8b6 --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t13.dart @@ -0,0 +1,66 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `FutureOr`, `FutureOr>`, `FutureOr?`, +/// `FutureOr>?`, `FutureOr`, `FutureOr?>`, `FutureOr?` or +/// `FutureOr?>?` and `C` is a type introduced by the type declaration +/// `D`, then the shorthand context denotes the type declaration `D`. Test an +/// enum. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import 'dart:async'; +import '../../Utils/expect.dart'; + +enum E { + e1(1), e2(2), e3("3"), e4("4"); + final T value; + const E(this.value); + + static E get staticGetter => E.e1; + static E staticMethod() => E.e2; + static E instance = E.e3; +} + +main() async { + FutureOr?>? e1 = .staticGetter; + Expect.equals(E.e1, await e1); + + FutureOr? e2 = .staticGetter; + Expect.equals(E.e1, await e2); + + FutureOr? e3 = .staticMethod(); + Expect.equals(E.e2, await e3); + + FutureOr?>? e4 = .staticMethod(); + Expect.equals(E.e2, await e4); + + FutureOr?>? e5 = .instance; + Expect.equals(E.e3, await e5); + + FutureOr? e6 = .instance; + Expect.equals(E.e3, await e6); + + E? e7 = .e4; + Expect.equals(E.e4, await e7); + + E? e8 = .e4; + Expect.equals(E.e4, await e8); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t14.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t14.dart new file mode 100644 index 0000000000..774453878e --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t14.dart @@ -0,0 +1,65 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `C`, `C<...>`, `C?`, or `C<...>?` and `C` is a type introduced by the +/// type declaration `D`, then the shorthand context denotes the type +/// declaration `D`. Test an extension type. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import '../../Utils/expect.dart'; + +extension type ET(T value) { + ET.id(this.value); + factory ET.f(T t) = ET; + + static ET get staticGetter => ET(4); + static ET staticMethod(X x) => ET(x); + static ET instance = ET("one"); +} + +main() { + ET? et1 = .new(1); + Expect.equals(1, et1.value); + + ET? et2 = .id(2); + Expect.equals(2, et2.value); + + ET? et3 = .f(3); + Expect.equals(3, et3.value); + + ET? et4 = .staticGetter; + Expect.equals(4, et4.value); + + ET? et5 = .staticGetter; + Expect.equals(4, et5.value); + + ET? et6 = .staticMethod(6); + Expect.equals(6, et6.value); + + ET? et7 = .staticMethod(7); + Expect.equals(7, et7.value); + + ET? et8 = .instance; + Expect.equals("one", et8.value); + + ET? et9 = .instance; + Expect.equals("one", et9.value); +} diff --git a/LanguageFeatures/Static-access-shorthand/type_inference_A01_t15.dart b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t15.dart new file mode 100644 index 0000000000..4094de2a95 --- /dev/null +++ b/LanguageFeatures/Static-access-shorthand/type_inference_A01_t15.dart @@ -0,0 +1,68 @@ +// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file +// for details. All rights reserved. Use of this source code is governed by a +// BSD-style license that can be found in the LICENSE file. + +/// @assertion A context type scheme is said to denote a declaration in some +/// cases. Not all context type schemes denote a declaration. +/// If a type scheme `S`: +/// - has the form `C` or `C` where `C` is a type introduced by a +/// declaration `D` which must therefore be a type-introducing declaration, +/// which currently means a class, mixin, enum or extension type declaration, +/// then `S` denotes the declaration `D`. +/// - has the form `S?` or `FutureOr`, and the type scheme S denotes a +/// declaration D, then so does `S?/FutureOr`. Only the "base type" of the +/// union type is considered, ensuring that a type scheme denotes at most one +/// declaration or static namespace. +/// - has any other form, including type variables, promoted type variables and +/// `_`, then the type scheme does not denote any declaration or namespace. +/// +/// @description Checks that if a shorthand context type schema has one of the +/// forms `FutureOr`, `FutureOr>`, `FutureOr?`, +/// `FutureOr>?`, `FutureOr`, `FutureOr?>`, `FutureOr?` or +/// `FutureOr?>?` and `C` is a type introduced by the type declaration +/// `D`, then the shorthand context denotes the type declaration `D`. Test an +/// extension type. +/// @author sgrekhov22@gmail.com + +// SharedOptions=--enable-experiment=enum-shorthands + +import 'dart:async'; +import '../../Utils/expect.dart'; + +extension type ET(T value) { + ET.id(this.value); + factory ET.f(T t) = ET; + + static ET get staticGetter => ET(4); + static ET staticMethod(X x) => ET(x); + static ET instance = ET("one"); +} + +main() async { + FutureOr? et1 = .new(1); + Expect.equals(1, (await et1)?.value); + + FutureOr?>? et2 = .id(2); + Expect.equals(2, (await et2)?.value); + + FutureOr? et3 = .f(3); + Expect.equals(3, (await et3)?.value); + + FutureOr?>? et4 = .staticGetter; + Expect.equals(4, (await et4)?.value); + + FutureOr? et5 = .staticGetter; + Expect.equals(4, (await et5)?.value); + + FutureOr?>? et6 = .staticMethod(6); + Expect.equals(6, (await et6)?.value); + + FutureOr? et7 = .staticMethod(7); + Expect.equals(7, (await et7)?.value); + + FutureOr?>? et8 = .instance; + Expect.equals("one", (await et8)?.value); + + FutureOr? et9 = .instance; + Expect.equals("one", (await et9)?.value); +}