-1

I was looking through other questions, but couldn't find any related to my problem. Basically I was writing a code to read some text files with data and process it later on. But I'm facing some weird problem that the values in array keeps on changing. Below I've given two 'for' loops, one where I read the values from file pointer and check it immediately with printf statement. The next 'for' loop is where I again check the values stored and for some reason it is different, with some random values.

        for (int i = 0; i < ndihedrals; ++i)
        {
            fscanf (readdihedral, "%d %f %d %d %d %d\n", &sino_dih[i], &angle_dih[i], &atom1_dih[i], &atom2_dih[i], &atom3_dih[i], &atom4_dih[i]);
            printf("i: %d ==> %d %f %d %d %d %d\n", i, sino_dih[i], angle_dih[i], atom1_dih[i], atom2_dih[i], atom3_dih[i], atom4_dih[i]);
        }

        for (int i = 0; i < ndihedrals; ++i)
        {
            printf("test2: i: %d ==> %d %f %d %d %d %d\n", i, sino_dih[i], angle_dih[i], atom1_dih[i], atom2_dih[i], atom3_dih[i], atom4_dih[i]);
        }

Here is the output from first for loop: (There are more lines, I'm just showing the first few lines of output from both for loops. I got these by putting sleep(1); statement after printf)

i: 0 ==> 1 -46.265598 696 698 699 700
i: 1 ==> 2 176.755005 696 698 699 701
i: 2 ==> 3 -56.561798 698 699 701 702
i: 3 ==> 4 168.240997 700 699 701 702
i: 4 ==> 5 172.516998 699 701 702 703
i: 5 ==> 6 -69.096497 699 701 702 704
i: 6 ==> 7 143.464005 701 702 704 705
i: 7 ==> 8 -98.824898 703 702 704 705
i: 8 ==> 9 149.878998 702 704 705 706
i: 9 ==> 10 -70.438004 702 704 705 707
i: 10 ==> 11 122.935997 704 705 707 708

Here is the output from second for loop:

test2: i: 0 ==> 1 0.000000 4533 4440 4441 4443
test2: i: 1 ==> 2 0.000000 4534 4442 4441 4443
test2: i: 2 ==> 3 0.000000 4535 4441 4443 4444
test2: i: 3 ==> 4 0.000000 4536 4441 4443 4444
test2: i: 4 ==> 5 0.000000 4537 632 633 635
test2: i: 5 ==> 6 0.000000 4538 634 633 635
test2: i: 6 ==> 7 0.000000 4539 633 635 636
test2: i: 7 ==> 8 0.000000 4540 633 635 636
test2: i: 8 ==> 9 0.000000 4541 635 636 638
test2: i: 9 ==> 10 0.000000 4542 637 636 638
test2: i: 10 ==> 11 0.000000 4543 636 638 639

Here is the declaration part for the code, I tried the code with both malloc and calloc.

        sino_dih = (int *) calloc (natoms, sizeof (int));
        atom1_dih = (int *) calloc (natoms, sizeof (int));
        atom2_dih = (int *) calloc (natoms, sizeof (int));
        atom3_dih = (int *) calloc (natoms, sizeof (int));
        atom4_dih = (int *) calloc (natoms, sizeof (int));
        angle_dih = (float *) calloc (natoms, sizeof (float));

I've attached the full code here (link: https://wetransfer.com/downloads/06c55057ecb6dade8af6407addadec6920180419090057/585c26)

My GCC version: 7.3.1 20180312
  • You have to check `fscanf()`'s return value before trusting what it "*read*". – Iharob Al Asimi Apr 19 '18 at 09:05
  • 2
    Posting a link to the code does not help, post a [mcve] instead. Or at least, the declaration and definition of your arrays. – Iharob Al Asimi Apr 19 '18 at 09:07
  • I checked the values using the printf statement within the first for loop, the values are correct. Or do you mean by some other method? – Raghuram Elancheran Apr 19 '18 at 09:07
  • No, `fscanf()` returns the number of matched specifiers. But that's not your problem right now, nontheless you should check it. Note that a `printf()` statement is not enough to be sure that something "*works*" because there is the concept of undefined behavior and in case your program is violating some basic rules and thus invoking undefined behavior, printing values will not be helpful. – Iharob Al Asimi Apr 19 '18 at 09:08
  • Can you tell me how I should check then? – Raghuram Elancheran Apr 19 '18 at 09:11
  • 1
    It's hard to know, please post the declarations of the arrays. Did you use `malloc()`? You can also use [valgrind](http://valgrind.org). – Iharob Al Asimi Apr 19 '18 at 09:16
  • Ok, I edited the post by adding mem allocation lines. I tried it with both malloc and calloc. I'll check out valgrind as well – Raghuram Elancheran Apr 19 '18 at 09:30
  • 1
    You used `natoms` and then `ndihedrals`, why? Why didn't you use `malloc()` instead of `calloc()`, any particular reason? Also, [read this](https://stackoverflow.com/questions/605845/do-i-cast-the-result-of-malloc). Please post all the information that would allow the reproduction of your problem, [mcve]. Because otherwise it's going to be really hard to help you. Thank you. – Iharob Al Asimi Apr 19 '18 at 09:32

1 Answers1

1

The size of your arrays is natoms, but you're accessing elements 0..ndihedrals-1. If natoms < ndihedrals there will be undefined behaviour. I guess you should allocate ndihedrals many elements, e.g.

sino_dih = calloc(ndihedrals, sizeof(int));
atom1_dih = ...
...

(I had to read the full code to come up with that)

Flopp
  • 1,887
  • 14
  • 24
  • 1
    [That's what I thought](https://stackoverflow.com/questions/49916974/inconsistent-values-in-gcc-array#comment86850407_49916974)! You had the time to read the whole code. Also, you could remove the cast from `calloc()` to indirectly indicate that it's not necessary, as well you could improve the excess of whitespace to make the code cleaner, also to indirectly indicate that there are better and more readable ways to write code. – Iharob Al Asimi Apr 19 '18 at 09:41
  • You're right. I wasn't aware of your comment when writing the answer, sorry :( – Flopp Apr 19 '18 at 09:44
  • Ok, I don't know why you're sorry. You answered the question correctly. – Iharob Al Asimi Apr 19 '18 at 09:58