Comparing Arrays for Equality in C++

Comparing two arrays in C, element by element

Your best bet is to rewrite it as a function that returns true or false (1 or 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.

You would use the above with

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

where the value N is #define'd per your question.

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 still a 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" true as 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.

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.

How to compare two arrays in C programming language?


scanf("%d", &array2);

You are never updating the index of array2 when getting a value from input.

Try

scanf("%d", &array2[i]);

As for comparing, you can also use memcmp to compare memory:

memcmp(array1, array2, sizeof(array1));

Equality of arrays In c

Use memcmp function to compare two arrays of equal length.

int a = memcmp(arr1, arr2, sizeof(arr1));
if(!a)
printf("Arrays are equal\n");
else
printf("Arrays are not equal\n");

Comparing arrays for equality in C++


if (iar1 == iar2)

Here iar1 and iar2 are decaying to pointers to the first elements of the respective arrays. Since they are two distinct arrays, the pointer values are, of course, different and your comparison tests not equal.

To do an element-wise comparison, you must either write a loop; or use std::array instead

std::array<int, 5> iar1 {1,2,3,4,5};
std::array<int, 5> iar2 {1,2,3,4,5};

if( iar1 == iar2 ) {
// arrays contents are the same

} else {
// not the same

}

compare two equal array in c but output shows unequal

When you do == with pointers (which is what str1 and str2 are in both cases1) all you are doing is comparing the two addresses to see if they are the same. When you do

char str1[]="hello";
char str2[]="hello";

You are creating two arrays on the stack that hold "hello". They are certainly at different memory locations, so str1 == str2 is false. This is like

char str1[6];
str1[0] = 'h';
str1[1] = 'e';
str1[2] = 'l';
str1[3] = 'l';
str1[4] = 'o';
str1[5] = '\0';

// and the same thing for str2

When you do

char *str1="hello";
char *str2="hello";

You are creating two pointers to the global data "hello". The compiler, seeing that these string literals are the same and cannot be modified, will make the pointers point to the same address in memory, and str1 == str2 is true.

To compare the content of two char*s, use strcmp:

// strcmp returns 0 if the two strings are equal
if (strcmp(str1, str2) == 0)
printf("Equal");
else
printf("Not equal");

This is roughly the equivalent of

char *a, *b;

// go through both strings, stopping when we reach a NULL in either string or
// if the corresponding characters in the strings don't match up
for (a = str1, b = str2; *a != '\0' && *b != '\0'; ++a, ++b)
if (*a != *b)
break;

// print Equal if both *a and *b are the NULL terminator in
// both strings (i.e. we advanced a and b to the end of both
// strings with the loop)
if (*a == '\0' && *b == '\0')
printf("Equal");
else
printf("Not equal");



1 In the char* version, this is true. In the char[] version, str1 and str2 are really arrays, not pointers, however when used in str1 == str2, they decay to pointers to the first elements of the arrays, so they are the equivalent of pointers in that scenario.

How to check if 2 c++ arrays are identical (all elements are the same, order matters) in O(1) or O(log n) time complexity?


It's not possible to ensure the equality of two arrays in less than O(N) time

Certainly, most algorithms are smart enough to "return early" upon realizing that two elements are not equal:

bool is_equal(std::array<int, 10> const& a, std::array<int, 10> const& b) {
for(size_t index = 0; index < 10; index++)
if(a[index] != b[index])
return false; //Return Early
return true;
}

But in order to verify that the arrays are equal, each individual element must be compared to their corresponding element in the other array. There's no way around this.

You could try to be sneaky, by precomputing hashes for the arrays at the time you create them.

auto[array, hash] = create_array();
auto[array2, hash2] = create_array(opt);

if(hash != hash2) {
std::cout << "Arrays are not equal in O(1) time!" << std::endl;
} else {
std::cout << "Arrays *might be* equal in O(1) time!" << std::endl;
}

But note how I've hedged with the equality check. Even if you have a fast way to compute the hash of the array, you can't verify the arrays are equal; you can only verify they are unequal. If the hash is big enough that it is 100% guaranteed to be unique for every possible set of values the array might contain, then comparing those two hashes together will still be proportional to the sizes of the array. This might be feasible if the domain of the array is extremely constrained (like we know the array can only contain a very small subset of known values for each index) but that's only applicable to a very small subset of problems, which probably does not represent your problem domain.

You could still get a speedup with the hash:

auto[array, hash] = create_array();
auto[array2, hash2] = create_array(opt);

if(hash != hash2) {
std::cout << "Arrays are not equal in O(1) time!" << std::endl;
} else {
if(array == array2)
std::cout << "Arrays *are definitely* equal (... but in O(N) time...)" << std::endl;
else
std::cout << "Arrays are not equal in O(N) time." << std::endl;
}

But note you still haven't broken O(N) time, you've simply improved your best-case runtime.

So no, no matter how you try to cheat the code, it's not possible to have an accurate equality comparison check between two arrays without having a runtime of O(N).

Compare two arrays and create new array with equal elements in C

As you have already figured out you can use merge sort (implementing it is beyond the scope of this answer, I suppose you can find a solution on wikipedia or searching on Stack Overflow) so that you can get nlogn + mlogm complexity supposing n is the size of the first array and m is the size of another.

Let's call the first array a (with the size n) and the second one b (with size m). First sort these arrays (merge sort would give us nlogn + mlogm complexity). And now we have:

a[n] // {2,2,2,4,5,7,8} and b[n] // {1,2,2,2,3,4,5,6,7,7,9}

Supposing n <= m we can simply iterate simulateously comparing coresponding values:

But first lets allocate array int c[n]; to store results (you can print to the console instead of storing if you need). And now the loop itself:

 int k = 0;  // store the new size of c array!
for (int i = 0, j = 0; i < n && j < m; )
{
if (a[i] == b[j])
{
// match found, store it
c[k] = a[i];
++i; ++j; ++k;
}
else if (a[i] > b[j])
{
// current value in a is leading, go to next in b
++j;
}
else
{
// the last possibility is a[i] < b[j] - b is leading
++i;
}
}

Note: the loop itself is n+m complexity at worst (remember n <= m assumption) which is less than for sorting so overal complexity is nlogn + mlogm. Now you can iterate c array (it's size is actually n as we allocated, but the number of elements in it is k) and do what you need with that numbers.

comparing two arrays in c++ and returning values depending on matches or non matches of elements

Decide in the inner loop, if 0 or 1 has to be printed, but print out in outer loop:

for(i)
{
char c = '0';
for(j)
{
if(==)
{
c = '1';
break;
}
}
std::cout << c << ' ';


Related Topics



Leave a reply



Submit