【问题标题】:qsort turns all values of array to nullqsort 将数组的所有值变为空
【发布时间】:2021-04-19 00:01:48
【问题描述】:

我有一个程序读取文本文件的行并将它们存储在linesArr 中,我还定义了一个函数compFunc,它将两个字符串作为输入,复制它们并将副本转换为小写在返回 strcmp(copy1, copy2) 的值之前。我正在尝试使用此功能将linesArrqsort(linesArr, size, 255, compFunc 按字母顺序排序。但数组中的值从{"Bob", "James", "Alice"} 变为{(null), (null), (null)}

这就是linesArr 的初始化方式。

char **linesArr = (char**)malloc(size*sizeof(char));
for (int i = 0; i < size; i++) {
    linesArr[i] = (char*)malloc(255*sizeof(char));
}

它使用文件指针fp从文本中填充值

for (int i = 0; i < size; i++) {    
    fgets(line, 255, fp);
    strcpy(linesArr[i], line);
}

为什么 qsort 会删除数组中的值?

【问题讨论】:

  • 你不应该使用 malloc 的 return。
  • 由于您没有在第一个 malloc 中分配正确的大小,因此您在其余代码中会出现未定义的行为。
  • malloc(size * sizeof(char)) 应该是 malloc(size * sizeof(char*))。所以linesArr 是它应该大小的 1/4 或 1/8。
  • 如果你想比较字符串而不考虑大小写,那么考虑检查你的实现是否提供stcasecmp()。使用它会比为每次比较制作修改后的字符串副本更有效。或者考虑自己编写——这不会那么难。

标签: c sorting dynamic-memory-allocation c-strings qsort


【解决方案1】:

对于初学者来说这个内存分配

char **linesArr = (char**)malloc(size*sizeof(char));
                                             ^^^^^

不正确,你需要写

char **linesArr = (char**)malloc(size*sizeof(char *));
                                             ^^^^^^

其次qsort的调用必须是这样的

qsort(linesArr, size, sizeof( char * ), compFunc);

因为指针linesArr指向的数组是指针数组。

这是一个演示程序。

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

int compFunc( const void *a, const void *b )
{
    const char *s1 = *( const char ** )a;
    const char *s2 = *( const char ** )b;
    
    while ( *s1 && tolower( ( unsigned char )*s1 ) == tolower( ( unsigned char )*s2 ) )
    {
        ++s1;
        ++s2;
    }
    
    return tolower( ( unsigned char )*s1 ) - tolower( ( unsigned char )*s2 );
}

int main(void) 
{
    enum { size = 3, len = 255 };
    
    char **linesArr = malloc( size * sizeof( char * ) );
    
    for ( size_t i = 0; i < size; i++ )
    {
        linesArr[i] = malloc( len * sizeof( char ) );
    }
    
    char line[len];
    
    for ( size_t i = 0; i < size; i++ )
    {
        fgets( line, sizeof( line ), stdin );
        line[ strcspn( line, "\n" ) ] = '\0';
        strcpy( linesArr[i], line );
    }
    
    qsort( linesArr, size, sizeof( *linesArr ), compFunc );
    
    for ( size_t i = 0; i < size; i++ )
    {
        puts( linesArr[i] );
    }
    
    for ( size_t i = 0; i < size; i++ )
    {
        free( linesArr[i] );
    }
    free( linesArr );
    
    return 0;
}

程序输出可能看起来像

Bob
James
Alice
Alice
Bob
James

【讨论】:

    猜你喜欢
    • 2013-04-20
    • 1970-01-01
    • 2015-10-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-10-10
    • 2018-06-24
    • 1970-01-01
    相关资源
    最近更新 更多