这是我关于Stack Overflow的第一个问题,对不起,如果写得不好。 我有一点问题。我用C编写了一个程序(我现在正在学习C,我是一个新手,我的第一语言,不要说我应该学习Python,拜托,因为我对C做得很好)。所以,我写了这个小程序。这是我尝试实现排序算法的尝试(我自己制作了算法,没有任何帮助或文档,我觉得效率非常低,我只是鬼混,虽然我不知道算法是否已经存在)。我所知道的唯一排序算法是QuickSort。 在任何情况下,这是最终的程序(有很多评论,以帮助我记住如果我再次访问它是如何工作的):
// trying to implement my own sorting algorithm
// it works the following way:
// for an array of n integers, find the largest number,
// take it out of the array by deleting it, store it
// at the very end of the sorted array.
// Repeat until the original array is empty.
// If you need the original array, simply
// make a copy of it before sorting
/***************************************/
// second implementation
// same sorting algorithm
// main difference: the program automatically
// computes the number of numbers the user enters
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>
int *sort(int *a, int n); // sort: the actual sorting function
char *read_line(char *str,int *num_of_chars); // read_line: reads input in string form
int *create_array(char *str, int n); // create_array: counts the num of integers entered and extracts them
// from the string the read_line function returns, forming an array
int size_of_array_to_be_sorted = 0; // of integers
int main(void)
{
int *array, i, *sorted_array, size = 3;
char *str = malloc(size + 1);
if (str == NULL)
{
printf("\nERROR: malloc failed for str.\nTerminating.\n");
exit(EXIT_FAILURE);
}
printf("Enter the numbers to be sorted: ");
str = read_line(str, &size);
array = create_array(str, size + 1);
sorted_array = sort(array, size_of_array_to_be_sorted);
printf("Sorted: ");
for (i = 0; i < size_of_array_to_be_sorted; i++)
printf("%d ", sorted_array[i]);
printf("\n\n");
return 0;
}
int *sort(int *a, int n)
{
int i, j, *p, *sorted_array, current_max;
sorted_array = malloc(n * (sizeof(int)));
if (sorted_array == NULL)
{
printf("ERROR: malloc failed in sort function.\nTerminating.\n");
exit(EXIT_FAILURE);
}
for (i = n - 1; i >= 0; i--) // repeat algorithm n times
{
current_max = a[0]; // intiliaze current_max with the first number in the array
p = a;
for (j = 0; j < n; j++) // find the largest integer int the array
if (current_max < a[j])
{
current_max = a[j];
p = (a + j); // make p point to the largest value found
}
*p = INT_MIN; // delete the largest value from the array
sorted_array[i] = current_max; // store the largest value at the end of the sorted_array
}
return sorted_array;
}
char *read_line(char *str, int *num_of_chars)
{
int i = 0; // num of chars initially
char ch, *str1 = str;
while ((ch = getchar()) != '\n')
{
str1[i++] = ch;
if (i == *num_of_chars) // gives str the possibility to
{ // dinamically increase size if needed
str1 = realloc(str, (*num_of_chars)++);
if (str1 == NULL)
{
printf("\nERROR: realloc failed in read_line.\nTerminating.\n");
exit(EXIT_FAILURE);
}
}
}
// at the end of the loop, str1 will contain the whole line
// of input, except for the new-line char. '\n' will be stored in ch
str1[i++] = ch;
str1[i] = '\0'; // store the null char at the end of the string
return str1;
}
int *create_array(char *str, int n)
{
int *array, i, j, k, num_of_ints = 0;
for (i = 0; i < n; i++) // computing number of numbers entered
if (str[i] == ' ' || str[i] == '\n')
num_of_ints++;
array = calloc((size_t) num_of_ints, sizeof(int)); // allocacting necessary space for the array
if (array == NULL)
{
printf("\nERROR: calloc failed in create_array.\nTerminating.\n");
exit(EXIT_FAILURE);
}
k = 0;
i = 1; // populating the array
for (j = n - 1; j >= 0; j--)
{
switch (str[j])
{
case '0': case '1': case '2':
case '3': case '4': case '5':
case '6': case '7': case '8':
case '9': array[k] += ((str[j] - '0') * i);
i *= 10;
break;
case '-': array[k] = -array[k]; // added to support negative integers
default: i = 1;
if (str[j] == ' ' && (str[j - 1] >= '0' && str[j - 1] <= '9'))
/* only increment k
*right before a new integer
*/
k++;
break;
}
}
// the loop works in this way:
// it reads the str string from the end
// if it finds a digit, it will try to extract it from the
// string and store in array, by adding to one of the elements
// of array the current char - ASCII for '0', so that it actually gets a digit,
// times the position of that digit in the number,
// constructing the number in base 10: units have 1, decimals 10, hundreds 100, and so on
// when it finds a char that's not a digit, it must be a space, so it resets i
// and increments k, to construct a new number in the next element of array
size_of_array_to_be_sorted = num_of_ints;
return array;
}
我自己写了所有内容,所以如果你认为我使用了一些不好的方法或天真的方法,请告诉我,以便我能够纠正它们。无论如何,我的问题是,在每次调用malloc,calloc或realloc之后,我都有这些'尝试处理错误'的语句。我有一台Linux机器和一台Windows机器。我在Linux上编写了程序,它有4GB的RAM。我编写它,用gcc编译,不得不改变一些东西,以使其工作,并运行完美。我没有问题。然后我将它复制到USB驱动器上,并在我的Windows机器上使用mingw进行编译,该机器具有8GB的RAM。我运行它,如果我给它超过3个2位整数,它会显示 错误:read_line中的realloc失败。 终止。 至少我知道'错误处理'如果语句有效,但为什么会这样呢?它是相同的代码,机器有两倍的RAM,其中大部分是免费的,它在Linux上运行没有问题。 这是否意味着我的代码不可移植? 这是我做不对的事吗? 算法错了吗? 该计划是非常非常低效的吗? 很抱歉这个问题很长。 谢谢,如果你想回答它。
答案 0 :(得分:3)
有问题的一行是:
str1 = realloc(str, (*num_of_chars)++);
其中*num_of_chars
是str
的当前大小。因为您正在使用 post-increment ,所以为新分配传递的值与当前值相同,因此您没有使str
更大,但请继续如果你有。