2013-04-18 77 views
2

以下代码片段显示std::vector C++库中的iterator。什么是C#等同于此?我是否可以简单地遍历向量中的每个项目,因为它不是链接列表?迭代器到底在做什么以及如何在C#中执行相同的操作?完整的代码是here什么是C#等价于std :: vector :: iterators?

std::vector<KMeanCluster>::iterator closest_cluster = clusters.begin(); 

    // Figure out which cluster this color is closest to in RGB space. 
    for (std::vector<KMeanCluster>::iterator cluster = clusters.begin(); 
     cluster != clusters.end(); ++cluster) { 
     uint distance_sqr = cluster->GetDistanceSqr(r, g, b); 

     if (distance_sqr < distance_sqr_to_closest_cluster) { 
     distance_sqr_to_closest_cluster = distance_sqr; 
     closest_cluster = cluster; 
     } 
    } 

回答

5

C++标准库迭代器的方式定义为表现得像是通过集合步行指针访问迭代器。在C#中,实现IEnumerable的每个集合都可以在foreach循环中迭代。除此之外,你仍然可以使用Enumerator C#的类似于C++迭代器的东西(这使得事情在大多数情况下更难):

IEnumerable<int> myCollection = new List<int> { 1, 2, 3 }; 
var enumerator = myCollection.GetEnumerator(); 
while(enumerator.MoveNext()) 
    Console.WriteLine(enumerator.Current); 

其实上面的是如何通过引擎盖下集合的foreach循环迭代。

foreach(int num in myCollection) 
    Console.WriteLine(num); 

因此,在你的代码而言,这是确切的(但很难编写和理解)等同:

IEnumerator<KMeanCluster> closest_cluster = clusters.GetEnumerator(); 
while (closest_cluster.MoveNext()) 
{ 
    uint distance_sqr = closest_cluster.Current.GetDistanceSqr(r, g, b); 
    if (distance_sqr < distance_sqr_to_closest_cluster) 
    { 
     distance_sqr_to_closest_cluster = distance_sqr; 
     closest_cluster = cluster; 
    } 
} 

,这是最简单的等同:

foreach(KMeanCluster closest_cluster in clusters) 
{ 
    uint distance_sqr = closest_cluster.GetDistanceSqr(r, g, b); 
    if (distance_sqr < distance_sqr_to_closest_cluster) 
    { 
     distance_sqr_to_closest_cluster = distance_sqr; 
     closest_cluster = cluster; 
    } 
} 
+0

优秀的答案。 –

2

迭代器基本上是一个允许对容器进行串行,非随机访问的对象。无论如何:你可以在C#中使用正常的循环。 foreach循环是有点接近C++原syntaxwise

2

在C#中,这可能是这样的:

var closest_cluster = clusters.FirstOrDefault(); 
foreach (var cluster in clusters) 
{ 
    uint distance_sqr = cluster.GetDistanceSqr(r, g, b); 
    if (distance_sqr < distance_sqr_to_closest_cluster) 
    { 
     distance_sqr_to_closest_cluster = distance_sqr; 
     closest_cluster = cluster; 
    } 
} 

什么foreach运营商所做的是它的使用IEnumerator下,这相当于你的迭代器。

+1

这将引发如果'clusters'不包含任何元素,则与C++代码不同。 'FirstOrDefault()'可能更合适。 – hvd

+0

@ hvd,当然。谢谢。 –

+0

当然,在尝试使用'closest_cluster' – JohnL

2

泛型集合 - IEnumerator<T>

支持在泛型集合上进行简单迭代。

非泛型集合 - IEnumerator

支持在非泛型集合上进行简单迭代。

这些是接口,应该继承和覆盖。方法如MoveNextReset。然后你可以在循环中使用这个类。

1

C#中有一个iterator构造,但在这种情况下,您不需要直接访问它,而是使用foreach循环。代码可能看起来像这样。

Cluster closestCluster = clusters.firstOrDefault(); 

foreach (Cluster currentCluster in clusters) 
{ 
    //Distance logic 
    if (distanceSqr < distanceSqrToClosestCluster) 
    { 
     closestCluster = currentCluster; 
    } 
} 

在内部,foreach通过IEnumerable<Cluster>接口

相关问题