Skip to content
Advertisement

Diifferetn result in Linux and Visual Studio

Does anybody know why compiling program in Visual Studio 2015 gives different result (those are correct I want to keep them) vs Linux Ubuntu (those are wrong).?

#include<stdio.h>
#include<string.h>
#include<ctype.h>

int main() {
    int i,j,k;
    int pair = 0;
    char array1[][12] = { "strike", "march", "play", "cool", "may", "july", 
                            "school", "bad", "good", "linux", "really" , "weird"};
    char word[12];
    char array2[][12] = {  "really", "mount", "hike", "bad", "linux", "weird","define"};
    for (i = 0; i < 12; i++) {
        for (j = 0; j < 12; j++) {
            if (strcmp(array1[i], array2[j])==0) {
                strcpy(word, array1[i]);
                for (k = 0; word[k]!=''; k++) {
                    word[k] = toupper(word[k]);
                }
                printf("%sn", word);
                pair++;
            }           
        }       
    }
    printf("nTotal pairs: %d", pair);
    getchar();
    return 0;
}

enter image description here

Advertisement

Answer

Reading beyond the end of an array invokes undefined behavior in C. Once your program invokes undefined behavior anything can happen or nothing at all. It is simply undefined. As aneesh correctly notes, the reason is due to iterating over 12 elements in array2 where ony 7 exist. This exposes one of the primary reasons filling your code with “magic numbers” (like 12) is a bad idea.

Instead, what you want to do is properly define constants for any specified quantity (such as your maximum number of characters in each string in array1 and array2) and then compute the value of any remaining quantities not previously defined.

The sizeof operator provides you with the method to determine the number of elements present in array1 and array2. For example:

a1elem = sizeof array1 / sizeof *array1;  /* get number of    */
a2elem = sizeof array2 / sizeof *array2;  /* elements in each */

for (i = 0; i < a1elem; i++) {      /* loop over valid range  */
    for (j = 0; j < a2elem; j++) {  /* for array1 & array2    */

(note: the sizeof operator can only be used to determine the sizeof an array where the declaration is visible within the present scope) For example, if you pass an array to a function you cannot use sizeof to determine the array size within the function.

Putting the pieces together, you could do something like the following and have it work correctly regardless of the operating system:

#include <stdio.h>
#include <string.h>
#include <ctype.h>

enum { MAXL = 12 };

int main (void) {
    int a1elem, a2elem, i, j, k, pair = 0;
    char array1[][MAXL] = { "strike", "march", "play", "cool", 
                            "may", "july", "school", "bad", 
                            "good", "linux", "really" , "weird"},
         array2[][MAXL] = { "really", "mount", "hike", 
                            "bad", "linux", "weird","define"},
         word[MAXL] = "";

    a1elem = sizeof array1 / sizeof *array1;  /* get number of    */
    a2elem = sizeof array2 / sizeof *array2;  /* elements in each */

    for (i = 0; i < a1elem; i++)         /* loop over valid range */
        for (j = 0; j < a2elem; j++)     /* for array1 & array2   */
            if (strcmp (array1[i], array2[j])==0) {
                strcpy (word, array1[i]);
                for (k = 0; word[k]; k++)
                    word[k] = toupper (word[k]);
                printf ("%sn", word);
                pair++;
            }           

    printf ("nTotal pairs: %dn", pair);
#if defined(_WIN32) || defined(_WIN64)
    getchar();
#endif
    return 0;
}

Example Use/Output

$ uname -snrmo
Linux valkyrie 4.7.4-1-ARCH x86_64 GNU/Linux

$ ./bin/arraysz
BAD
LINUX
REALLY
WEIRD

Total pairs: 4
User contributions licensed under: CC BY-SA
10 People found this is helpful
Advertisement