c阵列问题

时间:2011-05-02 17:56:36

标签: c arrays

我有一个这样的数组:

int sayilar[10] = {5,6,2,1,4,2,5,5,5,2};

现在我想得到一个结果:找到2个重复,5 = 4次,2 = 3次。

无法想象如何做到这一点。这是我的代码,这不正常:

#include <stdio.h>

int main()
{
    int sayilar[10]={5,6,2,1,4,2,5,5,5,2};
    int i,j;
    int matris[5][2];

    int ar[5];

    int temp=0;
    int tempX;
    int k=0;

    for(i=0; i<10; i++)
    {
        for(j=i+1; j<10; j++)
        {
            if(sayilar[j]==sayilar[i])
            {
                if(temp==0)
                {
                    matris[k][0] = sayilar[j];
                    matris[k][1] = 1;
                    temp=1;
                } else
                {
                    matris[k][1]++;
                }
            }
        }
        if(temp!=0)
        k++;
        temp=0;
    }

    printf("%d %d",matris[0][0],matris[0][1]+1);
}

4 个答案:

答案 0 :(得分:3)

您对阵列中的数字有什么了解吗?

例如,如果您知道它们都在1到10之间,那么您可以创建一个大小为10的数组,其中包含每个数字的计数。

像这样(未经测试)

int sayilar[] = {5,6,2,1,4,2,5,5,5,2};
int counts[10] = {};

for( int i=0; i<10; ++i)
{
    ++counts[sayilar[i]-1];
}

// Now the 'counts' array has:
// counts[0] == 1     - indicating one '1' found
// counts[1] == 3     - indicating three '2' found
// counts[2] == 0     - indicating zero '3' found
// etc.

如果您对sayilar中的值可能没有任何保证,那么首先排序可能是最好的选择,正如其他人所提到的那样。查看qsort,它会对您的阵列进行就地排序。

答案 1 :(得分:2)

我认为在执行嵌套循环之前,您应该检查sayilar[i]是否在matris中。

for(i=0; i<10; i++)
{
    int found = 0;
    for (int l=0; l<k; l++)
    {
       if (matris[l][0] == sayilar[i]) { found = 1; break; }
    }

    if (!found) 
    {
        for(j=i+1; j<10; j++)
        {
            //...

如果你想要更高级的解决方案,你可以对具有O(nlogn)复杂度的数组进行排序,而不仅仅是通过排序的数组进行迭代......只是为了灵感。

答案 2 :(得分:1)

理想情况下,您希望在一次传递中执行此操作,而不是使用嵌套循环。最好的方法是使用某种映射结构,其中map键是您计算的值,map值是该值的出现次数。

对于这个具体的例子,最简单的方法是创建一个单维数组,其中索引对应于你正在计算的值。例如:

int sayilar[10]={5,6,2,1,4,2,5,5,5,2};  
size_t counts[10] = {0};
size_t dups = 0;
...
for (i = 0; i < 10; i++)
{
  /**
   * Add one to the value of counts[k], where k == sayilar[i]
   */
  counts[sayilar[i]]++;

  /**
   * If the count is equal to 2, add one to the value
   * of dups.  We use == 2 instead of > 1 so that we
   * only count unique duplicates.  
   */
  if (counts[sayilar[i]] == 2)
  {
    dups++;
  }
}

因此,当此循环执行时,counts将更新如下:

counts[5] = 1;
counts[6] = 1;
counts[2] = 1;
counts[1] = 1;
counts[4] = 1;
counts[2] = 2; dups = 1;
counts[5] = 2; dups = 2;
counts[5] = 3;
counts[5] = 4;
counts[2] = 3;

不幸的是,如果您跟踪的是非常广泛的值或非整数值,则此方法无法很好地扩展。

像C ++和Java这样的语言提供了一种内置的地图数据类型,它通常建立在某种平衡树结构之上,如红黑树,超越这种特殊的过度杀伤问题。

答案 3 :(得分:0)

如果我正在写作,我会分两个阶段来完成。

首先,我循环遍历数组,并计算每个数组的实例:

int counts[5] = { 0,0,0,0,0 };

for ( int i=0 ; i < 10 ; ++i ) {
   counts[ sayilar[i] - 1 ] += 1;
}

接下来,我会循环查找重复项:

for( int i=0 ; i < 5 ; ++i ) {
   if ( counts[i] > 1 ) {
      printf("Duplicate found: %d with %d instances\n", i+1, counts[i] );
   }
}

这种方法使其更具可读性。