【问题标题】:Select an element by index from a .NET HashSet从 .NET HashSet 中按索引选择元素
【发布时间】:2011-04-19 05:49:30
【问题描述】:

目前我正在使用从HashSet 派生的自定义类。当我在特定条件下选择项目时,代码中有一点:

var c = clusters.Where(x => x.Label != null && x.Label.Equals(someLabel));

效果很好,我得到了这些元素。但是有没有一种方法可以接收集合中该元素的索引以与ElementAt 方法一起使用,而不是整个对象?

看起来或多或少是这样的:

var c = select element index in collection under certain condition;
int index = c.ElementAt(0); //get first index
clusters.ElementAt(index).RunObjectMthod();

手动迭代整个集合是更好的方法吗?我需要补充一点,它在一个更大的循环中,所以这个Where 子句针对不同的someLabel 字符串执行了多次。

编辑

我需要这个做什么? clusters 是一些文档集合的一组集群。文档按主题相似度分组。所以算法的最后一步是发现每个集群的标签。但是算法并不完美,有时它会产生两个或多个具有相同标签的集群。我想做的只是将这些集群合并成一个大集群。

【问题讨论】:

    标签: c# .net hashset


    【解决方案1】:

    如果您在 HashSet 中保存元素,有时需要通过索引获取元素,请考虑在这种情况下使用扩展方法 ToList()。因此,您使用 HashSet 的功能,然后利用索引。

    HashSet<T> hashset = new HashSet<T>();
    
    //the special situation where we need index way of getting elements
    List<T> list = hashset.ToList();
    
    //doing our special job, for example mapping the elements to EF entities collection (that was my case)
    
    //we can still operate on hashset for example when we still want to keep uniqueness through the elements 
    

    【讨论】:

    • 安全吗?我认为当您向 HashSet 添加元素时,这些项目可能会重新排序,并且对 ToList() 的后续调用可能并不总是产生相同的顺序。这只是一种预感,我没有看代码,MSDN也没有透露太多。
    • @uriDium 定义“安全”。重点不在于后续调用保持相同的顺序,而只是执行带有一些对象的函数。
    • 此工作错误在执行此操作时请牢记性能。 ToList() 是 O(N) 操作。
    【解决方案2】:

    没有哈希集的索引这样的东西。在某些情况下,哈希集提高效率的方法之一是不必维护它们。

    我也看不出这里有什么优势。如果您要获取索引,然后使用它,这将比仅获取元素效率低(获取索引将同样有效,然后您有一个额外的操作)。

    如果您想对同一个对象执行多个操作,只需按住该对象即可。

    如果您想对多个对象执行某项操作,请在遍历它们的基础上进行(正常foreach 或在Where() 的结果上执行foreach 等)。如果你想在几个对象上做某事,然后在这几个相同的对象上做其他事情,你必须分批进行,而不是在同一个foreach中进行所有操作,然后存储@的结果987654325@List&lt;T&gt;

    【讨论】:

      【解决方案3】:

      集合通常没有索引。如果位置对您很重要,您应该使用List&lt;T&gt; 而不是(或可能以及)一个集合。

      现在 .NET 4 中的 SortedSet&lt;T&gt; 略有不同,因为它维护了排序的值顺序。但是,它仍然没有实现IList&lt;T&gt;,所以ElementAt通过索引访问会很慢。

      如果您能详细说明您为什么需要此功能,那将会有所帮助。您的用例目前还不是很清楚。

      【讨论】:

      • 我已经按照你的要求添加了更详细的问题描述:)
      • @Ventus:这并不能真正解释为什么您需要索引。如果您只想为每个匹配项运行一个方法,那么简单的 foreach 循环绝对是前进的方向……您是否有特殊原因需要索引?
      • 显然我的语言能力(我的意思是英语)并不完美,虽然我想同时修改集合中的 2 个元素。但是,您建议使用 List 而不是 set 是个好主意,因此问题解决了,您的回答也被接受了。
      • 您说“如果职位对您很重要,您应该使用List&lt;T&gt;”但是如果我想要我的收藏和订单中的唯一条目怎么办?
      • @whiteshooz:然后保持HashSet&lt;T&gt;List&lt;T&gt;,并使它们保持同步。我不相信 BCL 中有任何固定的实现可以保证保持位置。
      猜你喜欢
      • 2013-10-08
      • 2021-09-28
      • 1970-01-01
      • 2020-03-18
      • 1970-01-01
      • 2012-12-28
      • 2022-11-24
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多