Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/377.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 制作许多通用对象的最佳方法_Java_Oop_Class - Fatal编程技术网

Java 制作许多通用对象的最佳方法

Java 制作许多通用对象的最佳方法,java,oop,class,Java,Oop,Class,背景 对于类,我制作了一个线性链接哈希表。它存储一个链表数组,每当调用get或put时,键都会被散列并按数组大小进行模化。然后对结果链表(我也实现了)调用get或put 我有一个ST(符号表)界面。它很像Map,但是Map所需的一些操作对我来说太混乱,无法实现。通过实现这个接口,我实现了链表、红黑树、线性探测哈希表和线性链接哈希表 我想创建一个类似于线性链接哈希表的东西,它接受任意委托符号表类型。例如,使用红黑树类型初始化它将生成一个红黑树表,get和put函数将委托给这些红黑树 我认识到,我的

背景

对于类,我制作了一个线性链接哈希表。它存储一个链表数组,每当调用get或put时,键都会被散列并按数组大小进行模化。然后对结果链表(我也实现了)调用get或put

我有一个
ST
(符号表)界面。它很像
Map
,但是
Map
所需的一些操作对我来说太混乱,无法实现。通过实现这个接口,我实现了链表、红黑树、线性探测哈希表和线性链接哈希表

我想创建一个类似于线性链接哈希表的东西,它接受任意委托符号表类型。例如,使用红黑树类型初始化它将生成一个红黑树表,get和put函数将委托给这些红黑树

我认识到,我的实现几乎肯定比库提供的实现慢,而且我最好在实际代码中使用这些实现。我只是在尝试和学习

问题

向哈希表提供类型的最佳方法是什么,以便哈希表由该类型的表组成,并且调用将委托给这些符号表

我不能使用泛型,因为我不能初始化它们,我需要在构造和重新调整大小时进行初始化


我考虑过提供一个所需类型的空白符号表来开始,然后使用
copy
方法,但似乎应该有更好的方法。是否有?

您可能还需要提供一个创建所需支持结构实例的
工厂

一个简单的例子是一个
映射
委托给另一个
映射

public static interface Supplier<T> {

    T get();
}

public static class DelegatingMap<K, V> implements Map<K, V> {

    private final Map<K, V> backingMap;

    public DelegatingMap(final Supplier<Map<K, V>> backingMapSupplier) {
        backingMap = backingMapSupplier.get();
    }

    @Override
    public int size() {
        throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
    }

    @Override
    public boolean isEmpty() {
        throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
    }
    //etc...
}
公共静态接口供应商{
T get();
}
公共静态类DelegatingMap实现Map{
私人最终地图备份地图;
公共授权地图(最终供应商支持地图供应商){
backingMap=backingMapSupplier.get();
}
@凌驾
公共整数大小(){
抛出新的UnsupportedOperationException(“尚未受支持”);//若要更改生成的方法体,请选择“工具”“模板”。
}
@凌驾
公共布尔值为空(){
抛出新的UnsupportedOperationException(“尚未受支持”);//若要更改生成的方法体,请选择“工具”“模板”。
}
//等等。。。
}

由于类型擦除,运行时对象不会自动跟踪其类型参数,这就是为什么
new t()
不会编译

您可以通过要求调用者为type参数提供
Class
对象来解决此问题,然后您可以使用该对象创建新实例。当然,使用反射会绕过编译时检查(尤其是编译器不会检查符号表实现是否具有所需的构造函数),也不会检查IDE可能提供的任何静态分析(构造函数上的调用层次结构不会显示任何调用方)


或者,您可以要求调用者向您提供factory对象,该对象可以根据需要创建符号表实现。这更灵活(例如,调用者可以选择构造函数参数)和静态类型安全,但也更详细…

您可能需要提供一个
工厂来创建所需支持结构的实例。参考:它创建长构造,但与
新HashtableSupplier类似(新LinkedListSupplier())
。有没有避免这种情况的技巧?使用静态方法创建一种
FactoryFactory
,为您的各种实现返回实例
Supplier
。感谢您的回答!虽然您的方法可行,但我发现在我的客户机中创建几个静态Supplier实例更容易。谢谢!我选择了factory对象选项(bmorris591对此作了更多解释)。