Generics in TypeScript: How to infer the type of an instance from the class - class

A factory function creates the instances of classes:
class A {
name: string
}
function factory<T>(Cl): T {
return new Cl()
}
let a = factory<A>(A)
a.name // OK
I would like to avoid the repetition of A in: factory<A>(A). The generics instance type should be able to be inferred from the class type, shouldn't be?
I tried this code:
function factory<T>(Cl: typeof T): T { // Error: Cannot find name 'T'
return new Cl()
}
Is there a way to do this?

Based on the Typescript documentation :
When creating factories in TypeScript using generics, it is necessary
to refer to class types by their constructor functions.
So you must do something like this:
function factory<T>(Cl: { new(): T; }): T {
return new Cl();
}
In the code above, Cl must a type that at least has a constructor which return T generic type.
So the type inference will work:
let a = factory(A);
a.name;
You don't need to specify the type of A anyway because the compiler know it.

Related

Dart - Limit generic constrained type to sub type

i am currently working with Flutter/Dart. I want to implement a generic helper class, which puts a received input value into a generic wrapper, depending on the type.
Here the example code:
class ClassA {}
class ClassB<T> {
ClassB(this.t);
final T t;
}
class ClassC<T extends ClassA? {
ClassC(this.t);
final T t;
}
class ClassD<T> {
ClassD(this.t);
final T t;
Object getWrapper(){
final t = this.t;
return T == ClassA?
? ClassC<T>(t) //<--fails
: ClassB<T>(t);
}
}
Produces:
'T' doesn't conform to the bound 'ClassA?' of the type parameter 'T'.
ClassD is the helper which produces the wrappers. For the wrapper ClassB there is no isdue, but i could not get it to work for the wrapper ClassC. As it constrains its generic type it conflicts with the generic type of the wrapper itself, although i also included a type check there to limit the type to the constrained one.
I am wondering why this won't work and how it could be adjusted to make it work.
I tried to add a type check and adjusted it in various ways like
T == ClassA
or
T is ClassA
also including the local variable t
T == ClassA && t is ClassA

Swift generic type defined by method context

Is there a name for a pattern where the type is inferred by the context of the result type?
Eg in this example what language could i use to document the foo method and explain that a type needs to be defined for the method to work?
protocol FooType {
init()
}
func foo<T: FooType>() -> T {
return T()
}
struct Bar: FooType {
init() {
print("bar")
}
}
let bar: Bar = foo()
// works returns instance of Bar
let fooType = foo()
// fails because foo doesn't know what type to use
You don't need to document this!
Everyone that writes code in Swift knows that to call a generic function, all its type parameters must be inferred and cannot be spoon-fed like this:
foo<Bar>()
People will see foo and say, "Oh I need the compiler to infer the type for this generic parameter." They will understand what this means.

error: type parameter `D` must be used as the type parameter for some local type

I'm using Nickel.rs with MongoDB to build a RESTful api.
I'd like to implement a generic Responder for the type mongodb::error::Result<Option<bson::Document>>.
This is the implementation I wrote based on the examples I found for Responder:
impl<D> Responder<D> for Result<Option<Document>> {
fn respond<'a>(self, mut response: Response<'a, D>) -> MiddlewareResult<'a, D> {
response.set(MediaType::Json);
match self {
Ok(Some(doc))=>{
ApiResponse{data: Bson::Document(doc).to_json()}.to_json()
},
Ok(None)=>{
response.set(StatusCode::NotFound);
ApiError{error: "Not found".to_string()}.to_json()
},
Err(e)=>{
response.set(StatusCode::InternalServerError);
ApiError{error: format!("{}",e)}.to_json()
}
}
}
}
and I'm getting the following error:
error: type parameter D must be used as the type parameter for some
local type (e.g. MyStruct<T>); only traits defined in the current
crate can be implemented for a type parameter [E0210]
I ran rustc --explain E0210 for an explanation and if my understanding is correct, I need to provide a trait D as a type argument to impl<D>, but I don't understand which trait to provide.
I tried impl<D: =()> but that produced the same error.
When you implement a trait then either the trait or the type you are implementing it for must be defined in the same crate. In you example that is not the case: the trait Responder is defined by nickel, and Result is defined by mongodb.
The common way to work around this is to define your own type, by wrapping the desired type into a tuple struct with a single component (the so-called newtype pattern):
struct Result(mongodb::error::Result<Option<Document>>);
impl Responder for Result {
...
Based on starblue's answer, I replaced ApiResponse and ApiError with a tuple struct and refactored my code as follows:
struct ApiResponse<T>(T);
impl<D> Responder<D> for ApiResponse<Result<Option<Document>>> {
fn respond<'a>(self, mut response: Response<'a, D>) -> MiddlewareResult<'a, D> {
let mut d = BTreeMap::new();
match self.0 {
Ok(Some(doc))=>{
d.insert("data".to_string(),Bson::Document(doc).to_json());
},
Ok(None)=>{
response.set(StatusCode::NotFound);
d.insert("error".to_string(),"Not Found".to_json());
},
Err(e)=>{
response.set(StatusCode::InternalServerError);
d.insert("error".to_string(),format!("{}",e).to_json());
}
}
response.set(MediaType::Json);
response.send(Json::Object(d))
}
}

Can I cast a metaclass object to a protocol type in Swift?

Swift inherited Objective-C's metaclass concept: classes themselves are also considered objects. A class Foo's object's class is Foo.self, and it is of type Foo.Type. If Foo inherits from Bar, then Foo.self can be assigned to a variable of type Bar.Type, too. This has at least two benefits:
it allows to override "static methods";
it's easy to create an instance of an unknown class in a type-safe way and without using reflection.
I'm particularly looking at the second one right now. Just to be sure that everybody understands what I'm after, here's an example:
class BaseFoo {
var description: String { return "BaseFoo" }
}
class DerivedFoo: BaseFoo {
override var description: String { return "DerivedFoo" }
}
let fooTypes: [BaseFoo.Type] = [BaseFoo.self, DerivedFoo.self] // metaclass magic!
for type in fooTypes {
let object: BaseFoo = type() // metaclass magic!
println(object)
}
Now, I have an array of AnyClass objects (any metaclass instance can be assigned to AnyClass, just like any object can be assigned to AnyObject), and I want to find which ones implement a given protocol. The protocol would declare an initializer, and I would instantiate the class just like I do in the example above. For instance:
protocol Foo {
init(foo: String)
}
class Bar: Foo {
required init(foo: String) { println("Bar initialized with \(foo)") }
}
class Baz {
required init() { println("I'm not a Foo!") }
}
let types: [AnyClass] = [Bar.self, Baz.self]
So far so good. Now, the problem is determining if the class implements the protocol. Since metaclass instances are polymorphic, I'd expect to be able to cast them. However, I'm apparently missing something, because Swift won't let me write this:
for type in types {
if let fooType = type as? Foo.Type {
let obj = fooType(foo: "special snowflake string")
}
}
The compiler error I get is:
error: 'Foo' is not identical to 'AnyObject'
Is there any way to determine if a metaclass instance represents a class that implements a protocol, and is there any way to cast that instance into a protocol type?
I tried to declare Foo as a class protocol, but it's apparently not enough.
EDIT: I just tried with the Any type, and while it doesn't cause a syntax error, it crashes the Swift compiler.
As of Xcode 7 beta 2 and Swift 2 it has been fixed. You can now write:
for type in types {
if let fooType = type as? Foo.Type {
// in Swift 2 you have to explicitly call the initializer of metatypes
let obj = fooType.init(foo: "special snowflake string")
}
}
Or if you only want type as type Foo.Type you can use for case
for case let type as Foo.Type in types {
let obj = type.init(foo: "special snowflake string")
}

How to initialize empty variables from your own type in Scala?

My problem is understanding is the syntax of Scala. I come from a Java background. I am trying to make a variable of the same type as the class it is in. Example:
class Exp {
var exp1: Exp;
}
I am getting this error:
Driver.scala:4: error: class Exp needs to be abstract, since variable exp1 is not defined
(Note that variables need to be initialized to be defined)
class Exp {
Can someone explain why I cannot do this? I am new to the language. Any explanation would help in understanding it better.
Because you need to initialize it. Otherwise the compiler thinks you want only the variable's interface: the getter and setter methods. It's very similar to how a method without a body is abstract. The following will initialize it to null and give you a valid concrete class with a concrete variable.
class Exp {
var exp1: Exp = _;
}
This use of _ means "default value" where the default is null for reference types and 0, false, or something similar for non-reference types.
Wildcard Initializer
in Scala 2:
var x: A = _
in Scala 3:
var x: A = scala.compiletime.uninitialized