I am writing a program for counting characters from a binary file. The number of characters counts, outputs, but after counting, instead of completing the program, such an exception pops up.

enter image description here

It does not point to my code, it points to the istype.c file. I went and looked at line 68

_ASSERTE(c >= -1 && c <= 255); 

I suppose that I had missed some encoding, because if my code were cursed, everything would point to it.

The debugger shows all the correct values ​​correctly.

Part of the code (the number of repeated characters is displayed here)

 void calculate_symb(FILE* fd) { int max = 0; fd = fopen("test.dat", "rb"); if (!fd) printf("Ошибка!Файл не найден!\n"); else { fseek(fd, 0L, SEEK_END); long fsize = ftell(fd); int n = fsize; cout << "Количество символов в файле = " << fsize << endl; char* symv = new char[n]; fseek(fd, 0L, SEEK_SET); cout << "Вывод содержимого двоичного файла:" << endl; for (int i = 0; i < n; i++) { fread(symv, sizeof(char), n, fd); cout << symv[i]; } fclose(fd); cout << endl; cout << "Повторяющиеся символы" << endl; for (int x = 0; x < 255; x++) { bool flag = true; if (isalnum(symv[x])) for (int y = x - 1; y >= 0 && flag; y--) if (symv[x] == symv[y]) flag = false; if (flag && isalnum(symv[x])) cout << "\"" << symv[x] << "\"" << " -> " << count(symv, symv + 255, symv[x]) << endl; } } } 
  • Can you see the code? - yrHeTaTeJlb
  • If it's not a secret, why should you pass FILE*fd as a parameter? ... And who will free up memory under symv ? And - it does not bother you that the program gives incorrect results (where are the two r in your word?)? - Harry

2 answers 2

We will not touch the algorithm itself - as we see, it does not work. But it does not work, in particular, because you have at least a call beyond the bounds of the array - with x >= n . And this alone theoretically leads to undefined behavior.

The meaning of the error is that some of the functions is... - apparently isalnum - passed a value that goes beyond char and EOF - are you aware that the argument of these functions is int ?

Where exactly and how exactly this happens - it makes sense to look at the presence of a minimal reproducible code.

For now, sort out the algorithm. As an option - this one, simpler :) Not the best option, but just to edit your code less, left a hard-coded file and read through fread , in general, you have where to turn around :) The same checks for "literalization" (at least for the beauty of the output, if there are any line breaks, for example) insert yourself.

 void calculate_symb() { FILE * fd = fopen("test.dat","rb"); if (!fd) printf("Ошибка!Файл не найден!\n"); else { int symv[256] = { 0 }; int fsize = 0; cout<<"Вывод содержимого двоичного файла:"<<endl; char symbol; while(fread(&symbol, sizeof(char), 1, fd)) { fsize++; cout << symbol; symv[symbol]++; } fclose(fd); cout<<"Количество символов в файле = "<<fsize<<endl; cout<<"Повторяющиеся символы"<<endl; for(int x = 0; x<=255; x++) { if (symv[x]) cout << "\"" << (char)x << "\" -> " << symv[x] << endl; } } } 

    The problem was solved in this way

    1) To start, add a null terminator '\ 0'for its string.

    2) Plus, the step-by-step debugger in the variable l added a kryakozyabru symbol to the line, hence he cursed the exception because he did not understand what character it was and could not find it simply among 255 names.

    3) Yes, he incorrectly counted the number of letters and this problem was also solved by adding the variable l to the loop, which reads the number of characters from the string using strlen.

    Corrected code snippets (before loop)

     char* symv = new char[n]; symv[n+1]='\0'; fseek(fd,0L,SEEK_SET); cout<<"Вывод содержимого двоичного файла:"<<endl; for(int i = 0; i<n; i++) { fread(symv, sizeof(char), n, fd); cout << symv[i]; } fclose(fd); cout<<endl; int l=strlen(symv); cout<<"Повторяющиеся символы:"<<endl; for(int x = 0; x<l-1; x++) 

    In the end, everything works without exceptions.

    enter image description here