新用户在这里进行堆叠交换,所以如果我不正确地问这个问题,我很抱歉。
我有一个创建程序的赋值,用于使用动态内存分配将用户输入的文本行分配给字符指针数组。
输入所有行后,将打印行。然后通过将第5行和第6行移动到末尾并且向前移动线('向上')来操纵它们。最后,行必须按字母顺序排序。我的问题在于:我无法获得一个排序函数来处理一个char指针数组。
我的代码发布在下面。我不确定我的sort函数是否正确引用了char指针。我也不确定我的变量是否正确,并且我无法确定我是否正确地将char字符串分配给char指针数组中的char指针。你能帮我解决这些问题吗?
非常感谢, r4mulus
//Program to collect lines of text, shift them in various ways and sort them, and output all the lines at each stage
// Declare libraries
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
// Declaring macros
#define len1 80
// Prototpying functions
void sortLine(char **, int size);
void swap(char **, char **);
// Main body of program
int main (void){
char *line_array[40];
char *(*ptr_all) = &line_array[0];
char buffer[80];
int ch;
int counter = 0;
// Loop to intake lines of text
do {
// Ask user to input a line of text
printf("Please input a line of text to store into memory. Enter '#' to stop collecting lines:\n");
fgets(buffer, len1+1, stdin);
// Check to make sure char '#' has not been entered
ch = buffer[0];
if (ch == '#'){
break;
}
// Measure the length of the line of text
unsigned long len = strlen(buffer);
// Allocate memory for the given line of text
line_array[counter] = (char *)malloc(len+1);
// Copy string in buffer into pointer to array of strings
strcpy(line_array[counter], buffer);
// Clear the buffer
for (int p = 0; p < (len1+1); p++){
buffer[p] = '\0';
}
// Increment the counter
counter++;
} while (counter < 40);
printf("\n");
// Print the lines collected so far
for (int q = 0; q < counter; q++){
printf("%s", line_array[q]);
}
printf("\n");
// Move lines of text 5 and 6 to the end; Move all other following lines forward two line spaces
char *temp_ptr1;
char *temp_ptr2;
temp_ptr1 = line_array[4];
temp_ptr2 = line_array[5];
for ( int r = 4; r < counter; r++){
line_array[r] = line_array[r+2];
}
line_array[counter-2] = temp_ptr1;
line_array[counter-1] = temp_ptr2;
// Print the rearranged lines
for (int s = 0; s < counter; s++){
printf("%s", line_array[s]);
}
printf("\n");
// Sort the lines alphabetically
sortLine(ptr_all, counter);
// Print the lines sorted alphabetically
for (int t = 0; t < counter; t++){
printf("%s", line_array[t]);
}
printf("\n\n");
// End the program
return 0;
}
功能
// Function to sort elements in an array
void sortLine(char **a, int size){
int i, j, compare;
for (i = 0; i < size; i++){
for (j = i; j < size; j++){
compare = strcasecmp((a[i]), (a[j]));
if (compare > 0)
swap(&a[i], &a[j]);
}
}
}
// Function to swap elements in an array
void swap(char **a, char **b){
char *temp = *a;
*a = *b;
*b = temp;
}
答案 0 :(得分:0)
指出换行符将少于任何文本字符这一事实,您可以使用memcmp来比较行。
void swap(char **a, char **b);
void sortLine(char *a[], int size){
int i, j;
for (i = 0; i < size; i++){
for (j = i + 1; j < size; j++){
if(memcmp(a[i], a[j], 80) > 0){
swap(&a[i], &a[j]);
}
}
}
}
void swap(char **a, char **b){
char *temp = *a;
*a = *b;
*b = temp;
}
电话应该是:
sortline(line_array, counter);
答案 1 :(得分:0)
您的代码存在一些问题,特别是在处理指针和分配时,但最重要的是,您必须将其划分为更简单和有用的函数。 例如,当您应该编写函数时,您会多次重复代码来打印行:
void printLines( char ** ppc, unsigned int n ) {
for (int i = 0; i < n; i++) {
printf("%s", ppc[i]);
}
printf("\n"); /* Adds always an empty line at end */
}
您被分配使用动态分配,并且您显然希望将行存储在以null终止的char数组char**
的数组中,大小足以存储40个(我认为)最多80个字符的行。但是,当你声明char *line_array[40];
时,你会分配一个指向40个字符数组的指针,而不是指向char的40个指针。写一些函数代替:
char ** allocLines( unsigned int n ) {
char ** ppc = (char **) malloc(n * sizeof(char *));
if ( !ppc ) {
printf("Error, unable to allocate memory for %d lines, malloc returned a null pointer!\n",n);
exit(1);
}
return ppc;
}
char * allocLine( unsigned int n ) {
char * pc = (char *) malloc((n + 1) * sizeof(char));
if ( !pc ) {
printf("Error, unable to allocate memory for %d chars, malloc returned a null pointer!\n",n + 1);
exit(1);
}
}
void freeLines( char ** ppc, unsigned int n ) {
if ( ppc ) {
for ( int i = 0; i < n; i++ )
if ( ppc[i] ) free(ppc[i]);
free(ppc);
}
}
并在另一个函数中使用它们来读取这些行:
unsigned int readLines( char ** ppc, unsigned int max, FILE * stream ) {
unsigned int counter = 0;
unsigned int length_of_line;
char buffer[MAX_LINE_LENGTH];
char *pc;
printf("Please, input up to %d lines of text to store into memory. Enter '#' to stop collecting lines:\n", max);
while ( counter < max
&& fgets(buffer, MAX_LINE_LENGTH, stream) ) {
/* fgets return NULL if no character is read when reaching EOF. Usefull if you read a file instead of stdin */
if ( buffer[0] == '#' ) break; /* stop reading lines if user enter # */
length_of_line = strlen(buffer);
pc = allocLine(length_of_line); /* It automatically adds the extra space for the '\0' terminator */
strcpy(pc,buffer); /* You can easily write your own version of strlen() and strcpy() if you're not allowed to use too many library functions */
ppc[counter] = pc; /* You don't really need pc, you can use ppc[counter] directly */
/* Why do you clear the buffer? its values are overwritten by fgets() */
counter++;
}
return counter;
}
现在,要对比较两个字符串所需的行进行排序,但是重新编写srtcmp,我认为你可以编写一个更专业的函数:
char isFirstStringGreater( char * a, char * b ) {
int i = 0;
while(a[i]!='\0' && b[i]!='\0') {
if ( a[i] < b[i] ) return 0;
else if ( a[i] > b[i] ) return 1;
i++;
}
return a[i]=='\0' ? 0 : 1;
}
并在你的algorythm中使用它。顺便说一句,效率很低,但迟早你会学习(或谷歌)更好的选择。
void sortLines(char ** a, int n ) {
int i, j;
for (i = 0; i < n; i++){
for (j = i + 1; j < n; j++) {
if ( isFirstStringGreater(a[i], a[j]) )
swap(&a[i], &a[j]);
}
}
}
正如我已经提到的,你写的swap()并没有真正交换数组。
void swap( char ** a, char ** b ) {
char * temp;
temp = *a;
*a = *b;
*b = temp;
}
要按要求滑动元素,您可以考虑概括上一个函数:
void shiftNLinesToEnd( char ** ppc, unsigned int s, unsigned int n, unsigned int max ) {
char ** temp = allocLines(n);
unsigned int i;
for ( i = 0; i < n; i++ )
temp[i] = ppc[s+i];
for ( i = s + n; i < max; i++ ) /* it would be a good idea to check if max > n + s... */
ppc[i-n] = ppc[i];
for ( i = 0; i < max; i++ )
ppc[max - n + i] = temp[i];
free(temp);
}
现在你可以写一个更干净,更易读(我认为)的main():
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void swap( char ** a, char ** b);
void sortLines( char ** a, int size);
char isFirstStringGreater( char * a, char * b );
unsigned int readLines( char ** ppc, unsigned int max, FILE * stream );
void printLines( char ** ppc, unsigned int n );
void shiftNLinesToEnd( char ** ppc, unsigned int s, unsigned int n, unsigned int max );
char ** allocLines( unsigned int n );
char * allocLine( unsigned int n );
void freeLines( char ** ppc, unsigned int n );
#define MAX_LINE_LENGTH 82 /* enough space to store up to 80 character plus '\n', plus the '\0' */
#define MAX_N_OF_LINES 40
int main(void) {
char **lines;
unsigned int n_of_lines;
lines = allocLines(MAX_N_OF_LINES);
n_of_lines = readLines(lines, MAX_N_OF_LINES,stdin);
printf("\n%d lines read:\n\n",n_of_lines);
printLines(lines, n_of_lines);
shiftNLinesToEnd(lines, 4, 2, n_of_lines);
printf("Rearranged, lines 5 and 6 have been moved to the end:\n\n");
printLines(lines, n_of_lines);
sortLines(lines, n_of_lines);
printf("Alphabetically sorted:\n\n");
printLines(lines, n_of_lines);
freeLines(lines, n_of_lines); /* free memory before finish */
return 0;
}
希望它有所帮助。