为什么将这两种方法放在同一个类中是不合法的?
class Test{
void add(Set<Integer> ii){}
void add(Set<String> ss){}
}
Run Code Online (Sandbox Code Playgroud)
我明白了 compilation error
方法add(Set)具有与Test类型中的另一种方法相同的擦除add(Set).
虽然我可以解决它,但我想知道为什么javac不喜欢这个.
我可以看到,在许多情况下,这两种方法的逻辑非常相似,可以用一个方法代替
public void add(Set<?> set){}
Run Code Online (Sandbox Code Playgroud)
方法,但情况并非总是如此.
如果你想要有两个constructors接受这些参数的话,这是非常烦人的,因为那时你不能只改变其中一个的名字constructors.
我有以下测试类,它使用泛型来重载方法.它在使用javac编译时有效,无法在Eclipse Helios中编译.我的java版本是1.6.0_21.
我读到的所有文章都表明Eclipse是对的,这段代码不适用.但是,使用javac和run编译时,会选择正确的方法.
这怎么可能?
谢谢!
import java.util.ArrayList;
public class Test {
public static void main (String [] args) {
Test t = new Test();
ArrayList<String> ss = new ArrayList<String>();
ss.add("hello");
ss.add("world");
ArrayList<Integer> is = new ArrayList<Integer>();
is.add(1);
is.add(2);
System.out.println(t.getFirst(ss));
System.out.println(t.getFirst(is));
}
public String getFirst (ArrayList<String> ss) {
return ss.get(0);
}
public Integer getFirst (ArrayList<Integer> ss) {
return ss.get(0);
}
}
Run Code Online (Sandbox Code Playgroud) 因此,标题暗示我的问题有点奇怪和复杂.我知道我要做的事情打破了"好"编程实践的所有规则,但是嘿,如果我们不活一点,生活会怎样?
所以我做的是创建以下程序.(这不是一个更大的实验的一部分,真正尝试和理解泛型,所以一些功能名称可能有点乱序)
import java.util.*;
public class GenericTestsClean
{
public static void test2()
{
BigCage<Animal> animalCage=new BigCage<Animal>();
BigCage<Dog> dogCage=new BigCage<Dog>();
dogCage.add(new Dog());
animalCage.add(new Cat());
animalCage.add(new Dog());
animalCage.printList(dogCage);
animalCage.printList(animalCage);
}
public static void main(String [] args)
{
//What will this print
System.out.println("\nTest 2");
test2();
}
}
class BigCage<T> extends Cage<T>
{
public static <U extends Dog> void printList(List<U> list)
{
System.out.println("*************"+list.getClass().toString());
for(Object obj : list)
System.out.println("BigCage: "+obj.getClass().toString());
}
}
class Cage<T> extends ArrayList<T>
{
public static void printList(List<?> list)
{
System.out.println("*************"+list.getClass().toString());
for(Object …Run Code Online (Sandbox Code Playgroud) 我正在阅读"Java Generics and Collections"一书,并且遇到了这段代码,它应该编译并运行而不会出错
class Overloaded {
public static Integer sum(List<Integer> ints) {
int sum = 0;
for (int i : ints) sum += i;
return sum;
}
public static String sum(List<String> strings) {
StringBuffer sum = new StringBuffer();
for (String s : strings) sum.append(s);
return sum.toString();
}
}
Run Code Online (Sandbox Code Playgroud)
但是,此示例无法编译时出错
错误:(16,26)java:name clash:sum(java.util.List)和sum(java.util.List)具有相同的擦除
我能理解为什么这是一个错误.但是,本书特别提到这是允许的,因为编译器可以根据返回类型区分这两种方法.
然后我在Java中找到了这个线程 Type Erasure and Overloading:为什么这样做?
它还建议这个例子应该编译.知道什么导致编译失败?
我使用的是JDK 1.8.这最近是用Java 1.8改变的吗?如果这是相关的,我使用最新的IntelliJ IDEA作为IDE.