gpt4 book ai didi

java - Java泛型可以用值而不是类型参数化吗?

转载 作者:行者123 更新时间:2023-12-04 11:11:24 25 4
gpt4 key购买 nike

假设我想定义结构相似的类型,但不同的参数可能是整数或其他东西。
是否可以在 Java 中定义由整数甚至任意对象参数化的一系列类?
考虑以下伪代码(无法编译):

/** 
* String of a certain length n and a method to reduce to length n-1
*/
public class StringN<int n> {
private String str;
public StringN( String str) {
if(str.length() != n) {
throw new IllegalArgumentException("string is not of required length!");
}
this.str = str;
}

public StringN<n-1> reduce() {
return new StringN<n-1>(s.substring(0, s.length() - 1));
}

@Override
public String toString() {
return str;
}
}
我想到的其他更自然的例子是数学中的张量积,所以如果想定义例如,将参数“n”放在哪里?空间 R^n 作为 Java 类或在函数式编程中是 Function<> 的“arity” -空间。那么如何定义一组具有不同元数的类,由 n 参数化?
如果这在 Java 中是不可能的,那么这个概念是否存在于其他更多功能的语言中?它的正确名称是什么? (比如“参数化类”?)
编辑:作为对评论的 react ,最后一部分只是知道这样一个概念的总称,而不是绕道其他语言。

最佳答案

唉,Java 要求类型参数是类型(实际上,它甚至要求它们是引用类型),而且由于所有整数都是相同的类型,因此编译器无法根据整数的值来区分泛型。
通常的解决方法是为每个可能(或需要)的值声明一个单独的类型。要共享结构,您可以使用抽象基类。如果基类需要任何具体类型,子类可以将它们作为类型参数传递:

abstract class StringN<S extends StringN<S,P>, P extends StringN<P,?>>
implements Comparable<S> {

final String value;

protected StringN(String value, int n) {
if (value.length() != n) {
throw new IllegalArgumentException(value);
}
this.value = value;
}

@Override
public int compareTo(S o) {
return value.compareTo(o.value);
}

abstract P newP(String value);

public P removeLast() {
return newP(value.substring(0, value.length() - 1));
}
}

class String0 extends StringN<String0, String0> {

protected String0(String value) {
super(value, 0);
}

@Override
String0 newP(String value) {
throw new UnsupportedOperationException();
}
}

class String1 extends StringN<String1, String0> {

protected String1(String value) {
super(value, 1);
}

@Override
String0 newP(String value) {
return new String0(value);
}
}

class String2 extends StringN<String2, String1> {
protected String2(String value) {
super(value, 2);
}

@Override
String1 newP(String value) {
return new String1(value);
}
}

public class Test {
public static void main(String[] args) {
String2 s2 = new String2("hi");
String1 s1 = s2.removeLast();
s1.compareTo(s2); // compilation error: The method compareTo(String1) is not applicable for the arguments (String2)
}
}
如您所见,只要值集是有限的并且预先知道,您甚至可以教编译器进行计数:-)
但是,它变得相当笨拙且难以理解,这就是为什么很少使用此类解决方法的原因。

关于java - Java泛型可以用值而不是类型参数化吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/68653064/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com