没有数据重复的性能结构

时间:2016-08-28 16:23:02

标签: java

说我有以下课程:

public class Tagged {

    private List<String> tags;
}

public class ContainerOfTagged {

    private List<Tagged> tagged;
}

使用此结构,每当我需要找到具有特定标记的Tagged时,我需要遍历ContainerOfTagged中标记的所有标记,并迭代每个Tagged的所有标记。这可能会影响性能,具体取决于列表的大小。

一个简单的解决方案是更改ContainerOfTagged类以使用MapTagged列表中的映射标记:

public class ContainerOfTagged {

    private Map<String, List<Tagged>> tagMapping;
}

现在,我需要做的就是提供一个标记,Map将返回带有所述标记的所有Tagged。但是,通过执行此操作,我导致数据重复,因为TaggedContainerOfTagged类中都存在相同的标记。

那么,有没有办法通过不重复数据的性能解决方案来解决这个问题?

1 个答案:

答案 0 :(得分:2)

你不能真正避免“复制”标签,但请记住,你并没有真正复制它们,因为Lists和Maps只存储对标签字符串的引用,而不是值(但是,引用可能会占用自己相当多的空间。)

问题是您需要两个索引:

  1. 给定Tagged对象,您需要找到标签列表。
  2. 您需要找到Tagged对象,给定标记。
  3. 理想情况下,您的解决方案看起来像这样。您可以通过一种方法来管理标记,从而解决您对不同步事物的担忧。

    请注意,在Tagged中,您应该使用Set而不是列表来避免重复标记。

    public class Tagged {
        Set<String> tags;
    }
    
    public class TagContainer {
        Map<String, Tagged> tagIndex;
    
        public tag(String tag, Tagged tagged) {
            tagged.tags.add(tag);
            tagIndex.put(tag, tagged);
        }
    

    如果内存利用率是一个主要问题,您可以尝试某种参考压缩。使用此技术,您可以将标记存储在数组中,然后通过索引引用它们。如果你有足够的,你可以使用一个字节或短而不是引用,但代码会更麻烦,我不会推荐它。

    修改

    在我的第一篇文章中,我提出Tagged应该是一个名为Tagable的接口。这是更清洁,但延长了解决方案,所以我回到了一个班级。但是,您可以考虑使用Tagable接口并在Tagged类中实现它。

    public interface Tagable {
        Set<String> getTags;
        tag(String tag);
    }