You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardexpand all lines: docs/user-guide/06-interfaces-generics.md
+28-23
Original file line number
Diff line number
Diff line change
@@ -742,17 +742,17 @@ See [if-let syntax](convenience-features.html#if_let-syntax) for more details.
742
742
Extensions to Interfaces
743
743
-----------------------------
744
744
745
-
In addition to extending ordinary types, you can define extensions on interfaces as well:
745
+
In addition to extending ordinary types, you can define extensions on all types that conforms to some interface:
746
+
746
747
```csharp
747
748
// An example interface.
748
749
interfaceIFoo
749
750
{
750
751
intfoo();
751
752
}
752
753
753
-
// Extending `IFoo` with a new method requirement
754
-
// with a default implementation.
755
-
extensionIFoo
754
+
// Extend any type `T` that conforms to `IFoo` with a `bar` method.
755
+
extension<T:IFoo>T
756
756
{
757
757
intbar() { return0; }
758
758
}
@@ -765,42 +765,47 @@ int use(IFoo foo)
765
765
}
766
766
```
767
767
768
-
Although the syntax of above listing suggests that we are extending an interface with additional requirements, this interpretation does not make logical sense in many ways. Consider a type `MyType` that exists before the extension is defined:
769
-
```csharp
770
-
structMyType : IFoo
771
-
{
772
-
intfoo() { return0; }
773
-
}
774
-
```
768
+
Note that `interface` types cannot be extended, because extending an `interface` with new requirements would make all existing types that conforms
769
+
to the interface no longer valid.
775
770
776
-
If we extend the `IFoo` with new requirements, the existing `MyType` definition would become invalid since `MyType` no longer provides implementations to all interface requirements. Instead, what an `extension` on an interface `IFoo` means is that for all types that conforms to the `IFoo` interface and does not have a `bar` method defined, add a `bar` method defined in this extension to that type so that all `IFoo` typed values have a `bar` method defined. If a type already defines a matching `bar` method, then the existing method will always override the default method provided in the extension:
771
+
In the presence of extensions, it is possible for a type to have multiple ways to
772
+
conform to an interface. In this case, Slang will always prefer the more specific conformance
773
+
over the generic one. For example, the following code illustrates this behavior:
777
774
778
775
```csharp
776
+
interfaceIBase{}
779
777
interfaceIFoo
780
778
{
781
779
intfoo();
782
780
}
783
-
structMyFoo1 : IFoo
781
+
782
+
// MyObject directly implements IBase:
783
+
structMyObject : IBase, IFoo
784
784
{
785
785
intfoo() { return0; }
786
786
}
787
-
extensionIFoo
787
+
788
+
// Generic extension that applies to all types that conforms to `IBase`:
789
+
extension<T:IBase>T:IFoo
788
790
{
789
-
intbar() { return0; }
791
+
intfoo() { return1; }
790
792
}
791
-
structMyFoo2 : IFoo
793
+
794
+
inthelper<T:IFoo>(Tobj)
792
795
{
793
-
intfoo() { return0; }
794
-
intbar() { return1; }
796
+
returnobj.foo();
795
797
}
796
-
voidtest()
798
+
799
+
inttest()
797
800
{
798
-
MyFoo1f1;
799
-
MyFoo2f2;
800
-
inta=f1.bar(); // a == 0, calling the method in the extension.
801
-
intb=f2.bar(); // b == 1, calling the existing method in `MyFoo2`.
801
+
MyObjectobj;
802
+
803
+
// Returns 0, the conformance defined directly by the type
804
+
// is preferred.
805
+
returnhelper(obj);
802
806
}
803
807
```
808
+
804
809
This feature is similar to extension traits in Rust.
Copy file name to clipboardexpand all lines: source/slang/slang-diagnostic-defs.h
+1
Original file line number
Diff line number
Diff line change
@@ -554,6 +554,7 @@ DIAGNOSTIC(30832, Error, invalidTypeForInheritance, "type '$0' cannot be used fo
554
554
555
555
DIAGNOSTIC(30850, Error, invalidExtensionOnType, "type '$0' cannot be extended. `extension` can only be used to extend a nominal type.")
556
556
DIAGNOSTIC(30851, Error, invalidMemberTypeInExtension, "$0 cannot be a part of an `extension`")
557
+
DIAGNOSTIC(30852, Error, invalidExtensionOnInterface, "cannot extend interface type '$0'. consider using a generic extension: `extension<T:$0> T {...}`.")
557
558
558
559
// 309xx: subscripts
559
560
DIAGNOSTIC(30900, Error, multiDimensionalArrayNotSupported, "multi-dimensional array is not supported.")
0 commit comments