0

I have to write a program in C and have it read an input text file that I created and output to an output file and show the original numbers and then sort them. I have most of it working, but it gives me an error when trying to get past a certain number in just reading the original input. Here is my code:

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

//function prototypes

void sortNumbers(int *num, int count);

void swap(int *nums, int i, int j);

//main function

int main(int argc, char *argv[])

{

 //declare the variables

 int *numbers;

 int count = 0, i = 0;

 char input[20], output[20];

 FILE *fileIn, *fileOut;

 //allocate the default size of array to maximum of 100

 numbers = (int *)malloc(sizeof(int));

 //check the number of arguments at command line

 if (argc < 2)

 {

      printf("Please provide the input and output text file names as ./a.out name1 name2 \n");

      return 0;

 }

 //read the file names from command line

 else

 {

      sscanf(argv[1], "%s", input);

      sscanf(argv[2], "%s", output);

 }

 //open the files

 fileIn = fopen(input, "r");

 fileOut = fopen(output, "w");

 //condition to check whether the input file and output

 //file are able to open or not. If not print the error message

 if (fileIn == NULL)

 {

      printf("Input file %s cannot be opened.\n", input);

      return 0;

 }

 else if (fileOut == NULL)

 {

      printf("Output file %s cannot be opened. \n", output);

      return 0;

 }

 //read the data from the file

 else

 {

      fscanf(fileIn, "%d", &numbers[i]);

      printf("%d\n", numbers[i]);

      fprintf(fileOut, "%d\n", numbers[i]);



      while (!feof(fileIn))

      {    i++;     

          numbers = (int *)realloc(numbers,(i)*sizeof(int));

          fscanf(fileIn, "%d", &numbers[i]);

          printf("%d\n", numbers[i]);

          fprintf(fileOut, "%d\n", numbers[i]);                                       

      }

 }

 count = i;

 //close the files

 fclose(fileIn);



 printf("\n");

 //sort the elements in the array

 sortNumbers(numbers, count);

 fprintf(fileOut,"\nElements after sorting are: \n");

 printf("\nElements after sorting are: \n");

 //print the elements to the console and to the

 //output file

 for(i=0;i<count;i++)

 {

      fprintf(fileOut,"%d \n", numbers[i]);

      printf("%d \n", numbers[i]);

 }

 fclose(fileOut);

 return 0;

}

//sort algorithm using selection sort

void sortNumbers(int *num, int count)

{

 for (int i = 0; i < count; ++i)

 {

      int minIndex = i;

      for (int j = i + 1; j < count; ++j)

      {

          if(num[j]<num[minIndex])

               minIndex = j;

      }

      swap(num, minIndex, i);

 }   

}

//swap function

void swap(int *nums, int i, int j)

    {

 int temp = nums[i];

 nums[i] = nums[j];

 nums[j] = temp;

}
Joe
  • 61
  • 2
  • 3
  • 8

3 Answers3

2

i started as zero and you allocated 1, you should realloc i+1. As your program stands, you will read into a memory space beyond what you've allocated. Furthermore, count is not equal to i. i is an index which runs from 0 to 1 less than the count in your array. Setting count to i will make it one less than the actual size.

Les
  • 10,335
  • 4
  • 40
  • 60
1

I see couple of issues in your program:

  1. Your logic for reading and counting the number of successfully read numbers is wrong. It will be off by 1.

  2. You are allocating one less than the required number of objects in the call to realloc.

I would replace the contents of the final else {} block with:

else
{
   while ( fscanf(fileIn, "%d", &numbers[i]) == 1 )
   {
      printf("%d\n", numbers[i]);
      fprintf(fileOut, "%d\n", numbers[i]);
      ++i;
      numbers = realloc(numbers,(i+1)*sizeof(int));
   }
}

Also see Why is “while ( !feof (file) )” always wrong?.

Community
  • 1
  • 1
R Sahu
  • 204,454
  • 14
  • 159
  • 270
0

You're allocating i ints into numbers but you're accessing the ith element. This causes a memory access error. Change your realloc to:

numbers = (int *)realloc(numbers,(i+1)*sizeof(int));

Adam Lamers
  • 1,183
  • 7
  • 8