C语言 逐个元素比较 C 中的两个数组

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/24153883/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-02 11:09:37  来源:igfitidea点击:

Comparing two arrays in C, element by element

carrays

提问by LightningXI

I have been cracking my head at achieving something very simple in C in order to make my one of the programs (not written by me) in our computational physics project more dynamic: comparing two different arrays element by element in an if conditional.

我一直在努力在 C 中实现一些非常简单的东西,以便使我们的计算物理项目中的一个程序(不是我编写的)更加动态:在 if 条件中逐个元素地比较两个不同的数组。

#include <math.h>
#include <stdio.h>
#include "header.h"
const   int nParam = 10;
double  a[nParam], a_tmp[nParam];
double values[10000];

double FitParam(double x){
    int xindex;
    double value;

    xindex=(int) x;

    if (a_tmp[1]==a[1] && a_tmp[2]==a[2] && a_tmp[3]==a[3] && a_tmp[4]==a[4]){ 
        value=values[xindex];
        return(value);
    }

// code continues... (very long subroutine and there is recursion for
// the subroutine so this if statement above is very important).

The array a[ ] has a varying number of significant elements every time we run our program; for example, right now, we are using this subroutine for only elements [1] through [4]. However, in other cases, we will want to have fewer or more elements, say, up to 3 elements or up to 5 elements, respectively.

每次运行程序时,数组 a[ ] 都有不同数量的重要元素;例如,现在,我们仅将这个子程序用于元素 [1] 到 [4]。但是,在其他情况下,我们希望拥有更少或更多元素,例如分别最多 3 个元素或最多 5 个元素。

So essentially, I want to be able to rewrite the if statement above so that it is dynamic... in other words, if there are N elements considered, then it will do:

所以本质上,我希望能够重写上面的 if 语句,以便它是动态的……换句话说,如果考虑了 N 个元素,那么它会这样做

if (a_tmp[1]==a[1] && ... && a_tmp[N]==a[N]){}

if (a_tmp[1]==a[1] && ... && a_tmp[N]==a[N]){}

So this if conditional should vary whenever our number N of elements of interest is changed (N is defined as a #define in the header of this file, which I just named header.h).

因此,每当我们感兴趣的元素的数量 N 发生变化时,这个 if 条件就会发生变化(N 在这个文件的头文件中被定义为 #define,我只是将其命名为 header.h)。

I would greatly appreciate your support on this task. Thank you.

我将非常感谢您对这项任务的支持。谢谢你。

回答by Floris

Your best bet is to rewrite it as a function that returns true or false (1 or 0):

最好的办法是将其重写为返回 true 或 false(1 或 0)的函数:

int compareArrays(double a[], double b[], int n) {
  int ii;
  for(ii = 1; ii <= n; ii++) {
    if (a[ii] != b[ii]) return 0;
    // better:
    // if(fabs(a[ii]-b[ii]) < 1e-10 * (fabs(a[ii]) + fabs(b[ii]))) {
    // with the appropriate tolerance
  }
  return 1;
}

Note that it is usually bad practice to compare doubles for equality - you are better off comparing their difference, and making sure the absolute value is less than some tolerance.

请注意,比较双打的相等性通常是不好的做法 - 最好比较它们的差异,并确保绝对值小于某个公差。

Also note you are comparing elements 1 through n - C arrays start at 0 though.

另请注意,您正在比较元素 1 到 n - C 数组虽然从 0 开始。

You would use the above with

你会使用上面的

if (compareArrays(a, a_tmp, N)) {

where the value Nis #define'd per your question.

其中值N#define“根据您的问题d。

If you want to be "clever" and avoid a loop, you can write the following - it will stop ("short-circuiting") as soon as you reach the right number of comparisons. It is stilla Bad Idea to compare doubles for equality but I will leave that for another time (see comment in code above for a solution).

如果您想变得“聪明”并避免循环,您可以编写以下内容 - 一旦达到正确的比较次数,它就会停止(“短路”)。它还是一个坏主意来比较平等的双打,但我会留到另一个时间(见注释代码上面的解决方案)。

if(a[1]==a_temp[1] && (2 > N || (a[2]==a_temp[2] && (3 > N || (a[3]==a_temp[3]))))) {

This makes the "and the rest" trueas soon as you have compared the right number of terms - so it will stop evaluating terms (as you need). I am not convinced this is either faster, or better code - but it is"dynamic"... You can obviously make this expression as long as you would like; I just wrote the first three terms so you get the idea. I DO NOT RECOMMEND IT.

true一旦您比较了正确数量的术语,这就会生成“和其余部分” - 因此它将停止评估术语(根据您的需要)。我不相信这会更快,或者更好的代码——但它“动态的”……你显然可以根据自己的意愿做出这个表达式;我刚刚写了前三个术语,所以你明白了。我不推荐它。

As for the comparison of doubles, you might consider replacing

至于双打的比较,可以考虑更换

if(a == b)

with

if(closeEnough(a, b))

where you define the macro

定义宏的地方

#define closeEnough(a, b) (fabs((a)-(b)) < 1e-10 * (fabs(a) + fabs(b)))? 1 : 0

This will make sure that your doubles don't have to be "exactly equal" - depending on how you arrived at them, they will almost never be, and the relative tolerance of 1 part in 10^10 is usually plenty for most practical comparisons.

这将确保你的双打不必“完全相等”——这取决于你是如何得到它们的,它们几乎永远不会是,而且 10^10 中的 1 部分的相对容差对于大多数实际比较来说通常是足够的.

回答by dwerner

If it must be at compile time, there is nothing in the standard that provides for a repeating macro like that. As in another (question), for bounded N, you can prepare N macros that expand to your desired comparison.

如果必须在编译时,标准中没有任何内容提供这样的重复宏。与另一个(问题) 一样,对于有界 N,您可以准备 N 个宏来扩展到您想要的比较。

While yet another alternative is memcmp

而另一种选择是 memcmp

memcmp( data, data2, array_len_in_bytes );

reference

参考

回答by Pankrates

An implementation might be to loop over all the elements and set a flag when a difference is detected

一个实现可能是遍历所有元素并在检测到差异时设置一个标志

int i, N;
int is_equal = 1;

for (i=1; i<N; ++i) {
    if (a[i] != a_tmp[i]) {
        is_equal = 0;
        break;
    }
}

if (is_equal)
    printf("Arrays are equal");

回答by Abraham Hernandez

A simple implementation is a linear comparison between both arrays, it just iterate over the array length and check if (a[i] != b[i]), if so return false& break out of the iteration.

一个简单的实现是两个数组之间的线性比较,它只是遍历数组长度并检查if (a[i] != b[i]),如果是,则返回false并退出迭代。

See the example below:

请参阅下面的示例:

#include <stdio.h>

int compareArrays(int a[], int b[], int n)
{
  for (int i=0; i<n; ++i)
  {
      if (a[i] != b[i])
      {
          return -1;
      }
  }
  return 0;
}

int main()
{
    int arr1[4] = {3, 4, 5, 7};
    int arr2[4] = {3, 4, 5, 7};

    int arr3[4] = {1, 5, 3, 7};
    int arr4[4] = {3, 4, 5, 19};

    printf("Should be True %d\n", compareArrays(arr1, arr2, 4));
    printf("Should be False %d\n", compareArrays(arr3, arr4, 4));
    return 0;
}

You should get:

你应该得到:

Should be True 0
Should be False -1

Run it online this example: https://repl.it/@abranhe/compare-arrays-in-c

在线运行这个例子:https: //repl.it/@abranhe/compare-arrays-in-c

回答by Lakshmikanth Gr

Today i came across same kind of problem statement,i googled for solution for an hour and end up with no solution,the above all approaches are not correct solutions for the stated problem

今天我遇到了同样的问题陈述,我用谷歌搜索了一个小时的解决方案,最终没有解决方案,上述所有方法都不是针对所述问题的正确解决方案

The Better way to resolve above Problem is

解决上述问题的更好方法是

Sort the two arrays either in ascending or descending order, Then compare both the arrays.

按升序或降序对两个数组进行排序,然后比较两个数组。

#include<stdio.h>
 void sort_it(int a[], int size)
      {
       int i,j,temp=0;
       for(i=0;i<size;++i)
        {

        for(j=i+1;j<size;++j)

        {
            if(a[i]>a[j])
                {
                temp=a[i];
                a[i]=a[j];
                a[j]=temp;
                }
        }
    }
};

int compare(int size,int a[],int b[])
{ 
    int i,j,is_equal;
    for(i=0;i<size;i++)
    {
        for(j=0;j<size;j++)`enter code here`
        {
            if(a[i]!=b[j])
            {
            is_equal=0;
            }
            else
            is_equal=1;
        }

    }



return is_equal;
};

int main()
{
    int size=4,i,is_equal;
    int a[]={1,2,5,4};
    int b[]={1,7,4,2};

    sort_it(a,size);
    sort_it(b,size);
    is_equal=compare(4,a,b);
    if(is_equal)
        printf("arrays are equal\n");
    else
        printf("arrays are not equal\n");
    return (0);

}