You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言结构体字符串处理异常:词频统计结果不符合预期

C语言单词频率统计问题修复

问题描述

我在使用C语言结构体处理字符串时遇到问题,怀疑和strcpy()有关但解决不了。练习要求编写程序:输入若干单词,输出不同单词并按出现频率降序排列,每个单词前标注出现次数。我试过把scanf()换成fgets(),问题依然存在。以下是我的代码(还没实现按频率排序的函数):

原代码

/*
Write a program that prints the distinct words given as input, sorted in order of frequency of
decreasing occurrence. Precede each word with its number of occurrences.
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>

#define SIZE 30
#define MAXWORD 5

typedef struct word_dictionary{
    char ww[SIZE];
    int occ;
} word;

int is_in_bucket(char *str, word data[]){
    int j;

    for(j=0;j<MAXWORD;j++){
        if( strcmp(str,data[j].ww) == 0)
            return 1;
    }

    return 0;
}

void print_bucket(word data[]) {
    int i;
    
    for(i=0;i<MAXWORD;i++){
        printf("{%d, %s} ", data[i].occ, data[i].ww);
    }

    printf("\n");
}

void main( int argc, char **argv) {
    word bucket[MAXWORD];
    char aux[SIZE];
    int i;
    int x;
    int cond;

    for(i=0;i<MAXWORD;i++) {
        printf("Insert the word you want to save in the data structure: ");
        scanf("%s",aux);
        
        cond = is_in_bucket(aux,bucket);
        if(cond == 1) {
            bucket[i].occ = bucket[i].occ + 1;
            memset(aux,0,SIZE);
        } else {
            strcpy(bucket[i].ww, aux);
            bucket[i].occ = 1;
            memset(aux,0,SIZE);
        }
    }

    print_bucket(bucket);
    // print_occurrences();
    
    return;
}

实际输出

Insert the word you want to save in the data structure: dog
Insert the word you want to save in the data structure: cat
Insert the word you want to save in the data structure: dog
Insert the word you want to save in the data structure: dog
Insert the word you want to save in the data structure: mouse
{1, dog} {1, cat} {-1768437999, } {1, V} {1, mouse}

预期输出

Insert the word you want to save in the data structure: dog
Insert the word you want to save in the data structure: cat
Insert the word you want to save in the data structure: dog
Insert the word you want to save in the data structure: dog
Insert the word you want to save in the data structure: mouse
{3, dog} {1, cat} {1, mouse}

问题分析与修复

核心错误点

  1. 结构体数组未初始化:bucket数组的元素没有初始化,ww字段是随机内存中的垃圾字符串,occ是随机整数,导致strcmp判断错误,输出出现乱码。
  2. 重复单词处理逻辑错误:is_in_bucket只返回是否存在,没有返回对应单词的索引。当检测到重复时,错误地修改当前循环i位置的occ,而不是找到的那个重复单词的occ。
  3. 打印逻辑错误:遍历所有MAXWORD个元素,包括未使用的空元素,导致输出无效内容。

修复后的代码

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

#define SIZE 30
#define MAXWORD 5

typedef struct word_dictionary{
    char ww[SIZE];
    int occ;
} word;

// 返回单词在数组中的索引,不存在返回-1
int find_word_index(char *str, word data[]) {
    for(int j = 0; j < MAXWORD; j++) {
        // 只判断已初始化的元素(occ>0说明已经存了单词)
        if(data[j].occ > 0 && strcmp(str, data[j].ww) == 0) {
            return j;
        }
    }
    return -1;
}

void print_bucket(word data[]) {
    for(int i = 0; i < MAXWORD; i++) {
        // 只打印有有效数据的元素
        if(data[i].occ > 0) {
            printf("{%d, %s} ", data[i].occ, data[i].ww);
        }
    }
    printf("\n");
}

int main() {
    word bucket[MAXWORD] = {0}; // 初始化所有元素为0,ww会被设为空字符串,occ为0
    char aux[SIZE];
    int count = 0; // 记录已存储的不同单词数量

    for(int i = 0; i < MAXWORD; i++) {
        printf("Insert the word you want to save in the data structure: ");
        scanf("%s", aux);
        
        int idx = find_word_index(aux, bucket);
        if(idx != -1) {
            // 找到重复单词,增加对应索引的occ
            bucket[idx].occ++;
        } else {
            // 新单词,存入第一个空位置
            if(count < MAXWORD) {
                strcpy(bucket[count].ww, aux);
                bucket[count].occ = 1;
                count++;
            } else {
                printf("单词数量已达上限\n");
            }
        }
    }

    print_bucket(bucket);
    return 0;
}

修复说明

  • 初始化结构体数组:用= {0}初始化,确保ww为空字符串,occ为0,避免垃圾数据干扰。
  • 修改查找函数:find_word_index返回单词的索引,方便直接修改对应元素的occ,同时只判断已初始化的元素(occ>0)。
  • 调整存储逻辑:用count记录已存储的不同单词数量,新单词存入count位置,避免占用未使用的索引。
  • 优化打印逻辑:只打印occ>0的有效元素,不再输出垃圾内容。

内容的提问来源于stack exchange,提问作者Numero8

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.05 05:41:19