泛型 - 使用 this 从另一个调用参数化构造函数
Generics - Invoking a parametrized constructor from another using this
class 我有 2 个构造函数。参数化构造函数和非参数化构造函数。问题是我无法使用 this(...) 从另一个调用参数化的一个。但是,当我尝试从其他地方进行相同的调用(比如一个主要方法)时它会起作用
这是代码
package com.test.generics;
public class Key<T> {
private T t;
public Key(T t){
this.t = t;
}
public T getKey(){
return t;
}
}
然后
package com.test.generics;
public class KeyValueObject<T> {
private String value;
private Key<T> key;
public KeyValueObject(Key<T> k){
key = k;
value = "-1";
}
public KeyValueObject(String keyString){
this(new Key<String>(keyString)); //Here is the problem, this says the Constructor KeyValueObject<T>(Key<String> k) is undefined
}
public static void main(String[] args) {
Key<String> keyStr = new Key<String>("x");
KeyValueObject<String> keyValObj = new KeyValueObject<String>(keyStr); //I try the same thing from main method and it works.
}
}
为什么编译器说 "Constructor KeyValueObject(Key k) is undefined"。我确实定义了构造函数 KeyValueObject(Key k)。
同样在 main 方法中,我几乎在做同样的事情。如果重载的构造函数起作用,我可以使用 new KeyValueObject("x")
编译器错误是有道理的,因为代码不是类型安全的。
要了解原因,假设您写道:
KeyValueObject<Integer> kv = new KeyValueObject("not an Integer");
上面的代码会尝试使用 Key<String>
参数调用 KeyValueObject<Integer>(Key<Integer>)
,这显然是无效的。
KeyValueObject<T>
属性的声明类型:
private Key<T> key;
与构造函数调用中的类型参数不同:
public KeyValueObject(String keyString){
this(new Key<String>(keyString));
}
构造函数的泛型类型参数必须与属性的类型相匹配:
public KeyValueObject(T t){
this(new Key<T>(t));
}
正如我已经在评论中写的,你可以这样做:
public class Program {
public static void main(String[] args) {
KeyValueObject<String> [=10=] = new KeyValueObject<>(new Key<>("x")); //old school
KeyValueObject<String> = new KeyValueObject<>("x"); //boxing constructor
KeyValueObject<String> = KeyValueObject.make("x"); //factory method
}
}
class Key<T> {
T key;
public Key(T key){
this.key = key;
}
public T getKey(){
return key;
}
}
class KeyValueObject<T> {
//Solution 2: Create a factory method to handle the case `T` == `String`
static KeyValueObject<String> make(String value) {
return new KeyValueObject<>(value);
}
String value;
Key<T> key;
KeyValueObject(Key<T> key){
this.key = key;
this.value = "-1";
}
//Solution 1: Change `String` to `T`
KeyValueObject(T key){
this(new Key<>(key));
}
}
类型 Key<String>
不一定与 Key<T>
匹配,因此错误有效。 (可能会想到不安全的类型转换)
考虑实现这样的工厂方法:
public static KeyValueObject<String> createKeyValueObject(final String keyString) {
return new KeyValueObject<String>(new Key<String>(keyString));
}
或为了更好地利用通用可能性:
public KeyValueObject(T k) {
this(new Key<T>(k));
}
class 我有 2 个构造函数。参数化构造函数和非参数化构造函数。问题是我无法使用 this(...) 从另一个调用参数化的一个。但是,当我尝试从其他地方进行相同的调用(比如一个主要方法)时它会起作用
这是代码
package com.test.generics;
public class Key<T> {
private T t;
public Key(T t){
this.t = t;
}
public T getKey(){
return t;
}
}
然后
package com.test.generics;
public class KeyValueObject<T> {
private String value;
private Key<T> key;
public KeyValueObject(Key<T> k){
key = k;
value = "-1";
}
public KeyValueObject(String keyString){
this(new Key<String>(keyString)); //Here is the problem, this says the Constructor KeyValueObject<T>(Key<String> k) is undefined
}
public static void main(String[] args) {
Key<String> keyStr = new Key<String>("x");
KeyValueObject<String> keyValObj = new KeyValueObject<String>(keyStr); //I try the same thing from main method and it works.
}
}
为什么编译器说 "Constructor KeyValueObject(Key k) is undefined"。我确实定义了构造函数 KeyValueObject(Key k)。
同样在 main 方法中,我几乎在做同样的事情。如果重载的构造函数起作用,我可以使用 new KeyValueObject("x")
编译器错误是有道理的,因为代码不是类型安全的。 要了解原因,假设您写道:
KeyValueObject<Integer> kv = new KeyValueObject("not an Integer");
上面的代码会尝试使用 Key<String>
参数调用 KeyValueObject<Integer>(Key<Integer>)
,这显然是无效的。
KeyValueObject<T>
属性的声明类型:
private Key<T> key;
与构造函数调用中的类型参数不同:
public KeyValueObject(String keyString){
this(new Key<String>(keyString));
}
构造函数的泛型类型参数必须与属性的类型相匹配:
public KeyValueObject(T t){
this(new Key<T>(t));
}
正如我已经在评论中写的,你可以这样做:
public class Program {
public static void main(String[] args) {
KeyValueObject<String> [=10=] = new KeyValueObject<>(new Key<>("x")); //old school
KeyValueObject<String> = new KeyValueObject<>("x"); //boxing constructor
KeyValueObject<String> = KeyValueObject.make("x"); //factory method
}
}
class Key<T> {
T key;
public Key(T key){
this.key = key;
}
public T getKey(){
return key;
}
}
class KeyValueObject<T> {
//Solution 2: Create a factory method to handle the case `T` == `String`
static KeyValueObject<String> make(String value) {
return new KeyValueObject<>(value);
}
String value;
Key<T> key;
KeyValueObject(Key<T> key){
this.key = key;
this.value = "-1";
}
//Solution 1: Change `String` to `T`
KeyValueObject(T key){
this(new Key<>(key));
}
}
类型 Key<String>
不一定与 Key<T>
匹配,因此错误有效。 (可能会想到不安全的类型转换)
考虑实现这样的工厂方法:
public static KeyValueObject<String> createKeyValueObject(final String keyString) {
return new KeyValueObject<String>(new Key<String>(keyString));
}
或为了更好地利用通用可能性:
public KeyValueObject(T k) {
this(new Key<T>(k));
}