Is there a function that will quickly sort a file

2019-09-28 06:30发布

Right, I'm writing some code using databases, and someone at my school was talking about some specific command that could automatically get a file and sort it.

I think I have a grasp on how to sort this file manually, but it requires a lot of work, so I was wondering if anyone knew this function.

edit: using DEV C++ , Library #stdio.h and # conio.h , (i can add the extra library if necessary) no idea what the specific complier is however.

2条回答
叼着烟拽天下
2楼-- · 2019-09-28 06:55

As others have mentioned there is sort command in Unix:

sort myfile.txt

see man sort for more options.

And there is SORT command on Windows:

sort myfile.txt

or

SORT myfile.txt

for more help see: http://www.computerhope.com/sorthlp.htm

With that you could write simple C program that would use those commands.

// sort.system.c

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

int main(int argc, char **argv) {
  if (argc != 2) { // expecting one argument, file which we will sort
    fprintf(stderr, "Usage: sort [FILE]\n");
    return EXIT_FAILURE;
  }

  int length = 5 + strlen(argv[1]) + 1; // length of "sort " is 5.
  char *command = (char *) calloc(length, sizeof(char));
  sprintf(command, "sort %s", argv[1]);

  int ret = system(command);

  return ret;
}

Here we just expect from user to enter file he wants to sort and then we are using this file and just give it to sort command. But first we need to make sure that user actually entered something. That is why we have if on beginning of main function.

Second approach would be to write sort command ourself. The fun starts here. :D

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

#define MAX_LINE_LENGTH 1000000

// compare function for qsort function
int compare (const void *a, const void *b) {
  const char **s1 = (const char **) a;
  const char **s2 = (const char **) b;
  return strcmp(*s1, *s2);
}

int main(int argc, char **argv) {
  if (argc != 2) { // expecting one argument, file which we will sort
    fprintf(stderr, "Usage: sort [FILE]\n");
    return EXIT_FAILURE;
  }

  char *filename = argv[1]; // name of file to sort
  FILE *file = fopen(filename, "r"); // trying to open that file
  if (file == NULL) {
    fprintf(stderr, "Could not open file %s\n", filename);
    return EXIT_FAILURE;
  }

  int size = 16; // initial size of lines container
  char **lines = (char **) calloc(size, sizeof(char *)); // lines container
  if (lines == NULL) { // safety check
    fprintf(stderr, "Could not allocate the requested block of memory\n");
    return EXIT_FAILURE;
  }

  // buffer where we will store every line before putting it into line container
  char *buffer = (char *) calloc(MAX_LINE_LENGTH + 1, sizeof(char));
  if (buffer == NULL) { // safety check
    fprintf(stderr, "Could not allocate the requested block of memory\n");
    return EXIT_FAILURE;
  }

  int counter = 0; // line counter, counts how many lines we have readed

  // reading whole line into buffer
  while(fgets(buffer, MAX_LINE_LENGTH + 1, file) != NULL) {
    // measuring line length with strlen and adding 1 for '\0'
    int length = strlen(buffer);
    if (buffer[length - 1] == '\n') { // remove '\n' on end of line
      // replace '\n' with '\0', thus '\0' already included into length
      buffer[length - 1] = '\0';
    } else {
      length++; // include '\0'
    }

    // if our lines container is not large enough we will double its size
    if (counter + 1 == size) {
      size *= 2;
      lines = (char **) realloc(lines, size*sizeof(char *));
      if (lines == NULL) { // safety check
        fprintf(stderr, "Could not allocate the requested block of memory\n");
        return EXIT_FAILURE;
      }
    }

    // allocating space for line
    lines[counter] = (char *) malloc(length*sizeof(char));
    strcpy(lines[counter], buffer);

    counter++;
  }

  // using qsort function from stdlib.h
  qsort(lines, counter, sizeof(char *), compare);

  int i;
  for (i = 0; i < counter; i++) {
    puts(lines[i]);
  }

  return EXIT_SUCCESS;
}

Idea is to have some dynamic "lines container" whose initial size is 16. Every time we see that we need more space for storing our lines, we double the size of our "lines container".

Also, we have some buffer that we use to store every line and then we copy that line into next line container slot.

Here I limited size of one line to 10^6 characters. But you could dynamically allocate space for buffer too by using ftell and fseek functions. I suggest you to do that for practice. :)

For actual sorting of strings we are using qsort function from stdlib.h:

http://www.cplusplus.com/reference/cstdlib/qsort/

查看更多
Evening l夕情丶
3楼-- · 2019-09-28 07:03

assuming your input file is data.txt (Linux), you can use the system command sort:

sort data.txt > output.txt
查看更多
登录 后发表回答