求解C语言相关问题解答程序

给定一个文本文件data1.txt,编写程序完成如下任务:
(1)对于前10个小写英文字母、后10个大写英文字母、以及10个数字的每个字符。统计其在文件datal.txt中出现的次数;
(2)将上述字母及出现的次数按照出现次数由大到小的顺序写到文本文件data2.txt中。

可参考采纳

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

#define LETTER_COUNT 26
#define DIGIT_COUNT 10

int main() {
    char filename[] = "data1.txt";
    char outfilename[] = "data2.txt";
    int letter_count[LETTER_COUNT + DIGIT_COUNT] = {0};
    int i, j, max_count, max_index;
    char c;
    FILE *fp, *outfp;

    // 打开数据文件
    fp = fopen(filename, "r");
    if (fp == NULL) {
        printf("无法打开文件 %s\n", filename);
        return 1;
    }

    // 统计字符出现次数
    while ((c = fgetc(fp)) != EOF) {
        if (c >= 'a' && c <= 'z') {
            letter_count[c - 'a']++;
        } else if (c >= 'A' && c <= 'Z') {
            letter_count[c - 'A' + LETTER_COUNT]++;
        } else if (c >= '0' && c <= '9') {
            letter_count[c - '0' + LETTER_COUNT + LETTER_COUNT]++;
        }
    }

    // 关闭数据文件
    fclose(fp);

    // 打开输出文件
    outfp = fopen(outfilename, "w");
    if (outfp == NULL) {
        printf("无法打开文件 %s\n", outfilename);
        return 1;
    }

    // 按照出现次数排序并输出到文件
    for (i = 0; i < LETTER_COUNT + DIGIT_COUNT; i++) {
        max_count = -1;
        max_index = -1;
        for (j = 0; j < LETTER_COUNT + DIGIT_COUNT; j++) {
            if (letter_count[j] > max_count) {
                max_count = letter_count[j];
                max_index = j;
            }
        }
        if (max_count > 0) {
            fprintf(outfp, "%c: %d\n", max_index < LETTER_COUNT ? 'a' + max_index : 'A' + max_index - LETTER_COUNT, max_count);
            letter_count[max_index] = 0;
        }
    }

    // 关闭输出文件
    fclose(outfp);

    printf("任务完成!\n");

    return 0;
}

基于new bing的编写:
data1.txt测试部分数据:

img


写入data2.txt文件结果:

img

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

// 定义常量,包括文件名、字符集大小、最小最大ASCII码等
#define FILENAME "data1.txt"  // 输入文件名
#define OUTPUT_FILENAME "data2.txt"  // 输出文件名
#define NUM_LETTERS 62  // 字符集大小
#define NUM_LOWERCASE_LETTERS 26  // 小写字母个数
#define NUM_UPPERCASE_LETTERS 26  // 大写字母个数
#define NUM_DIGITS 10  // 数字个数
#define MIN_ASCII_LOWERCASE 97  // 小写字母的最小ASCII码值
#define MAX_ASCII_LOWERCASE 122  // 小写字母的最大ASCII码值
#define MIN_ASCII_UPPERCASE 65  // 大写字母的最小ASCII码值
#define MAX_ASCII_UPPERCASE 90  // 大写字母的最大ASCII码值
#define MIN_ASCII_DIGIT 48  // 数字的最小ASCII码值
#define MAX_ASCII_DIGIT 57  // 数字的最大ASCII码值
 
int main() {
  // 初始化三个计数数组,分别对应小写字母、大写字母和数字
  int lowercase_counts[NUM_LOWERCASE_LETTERS] = {0};  // 小写字母计数数组
  int uppercase_counts[NUM_UPPERCASE_LETTERS] = {0};  // 大写字母计数数组
  int digit_counts[NUM_DIGITS] = {0};  // 数字计数数组
 
  // 打开指定文件进行读取
  FILE* fp = fopen(FILENAME, "r");  // 以只读模式打开输入文件
  if (fp == NULL) {  // 判断文件是否成功打开
    perror("Failed to open file"); // 输出错误信息
    exit(EXIT_FAILURE);  // 终止程序运行
  }
 
  char c;
  // 循环遍历文件中的每个字符,若是小写字母则增加小写字母计数数组相应位置的计数,
  // 若是大写字母则增加大写字母计数数组相应位置的计数,若是数字则增加数字计数数组相应位置的计数;
  while ((c = fgetc(fp)) != EOF) {  // 逐个读取文件中的字符,直到读取到文件结束符EOF
    if (islower(c)) {  // 使用islower()函数判断c是否为小写字母
      lowercase_counts[c - MIN_ASCII_LOWERCASE]++;  // 增加小写字母计数数组中相应位置的计数
    } else if (isupper(c)) {  // 使用isupper()函数判断c是否为大写字母
      uppercase_counts[c - MIN_ASCII_UPPERCASE]++;  // 增加大写字母计数数组中相应位置的计数
    } else if (isdigit(c)) {  // 使用isdigit()函数判断c是否为数字
      digit_counts[c - MIN_ASCII_DIGIT]++;  // 增加数字计数数组中相应位置的计数
    }
  }
 
  fclose(fp);  // 关闭输入文件
 
  // 创建结构体,保存每个字符以及各自的计数值,并对其按照计数值从大到小排序
  typedef struct {
    char letter;  // 字符本身
    int count;  // 字符出现的次数
  } LetterCount;

  // 计算总出现次数并创建结构体数组
  int total_counts = NUM_LOWERCASE_LETTERS + NUM_UPPERCASE_LETTERS + NUM_DIGITS;  // 计算字符总共出现的次数
  LetterCount counts[total_counts];  // 创建结构体数组,长度为字符总共出现的次数
 
  // 将字符和计数值存入结构体数组中
  int i, j;
  for (i = 0, j = 0; i < NUM_LOWERCASE_LETTERS; i++, j++) {  // 遍历小写字母计数数组
    counts[j].letter = (char)(i + MIN_ASCII_LOWERCASE);  // 存入字符
    counts[j].count = lowercase_counts[i];  // 存入相应位置的计数值
  }
  for (i = 0; i < NUM_UPPERCASE_LETTERS; i++, j++) {  // 遍历大写字母计数数组
    counts[j].letter = (char)(i + MIN_ASCII_UPPERCASE);  // 存入字符
    counts[j].count = uppercase_counts[i];  // 存入相应位置的计数值
  }
  for (i = 0; i < NUM_DIGITS; i++, j++) {  // 遍历数字计数数组
    counts[j].letter = (char)(i + MIN_ASCII_DIGIT);  // 存入字符
    counts[j].count = digit_counts[i];  // 存入相应位置的计数值
  }
 
  // 对结构体数组进行冒泡排序,实现按计数值从大到小排列的目的
  int swapped;
  do {
    swapped = 0;
    for (i = 1; i < total_counts; i++) {
      if (counts[i-1].count < counts[i].count) {  // 如果前面一个计数值比后面一个小,则交换两个结构体的顺序
        LetterCount temp = counts[i-1];  // 临时保存前面的结构体
        counts[i-1] = counts[i];  // 将后面的结构体赋值给前面的位置
        counts[i] = temp;  // 将保存的临时结构体赋值给后面的位置
        swapped = 1;  // 设置标志位为真,表示本轮有元素交换
      }
    }
  } while (swapped);  // 只要有元素交换,就再次执行循环
 
  // 打开指定输出文件进行写入,将排好序的结构体数组中的字符和计数值输出到指定文件中,并关闭输出文件
  fp = fopen(OUTPUT_FILENAME, "w");  // 以只写模式打开输出文件
  if (fp == NULL) {  // 判断文件是否成功打开
    perror("Failed to open file");  // 输出错误信息
    exit(EXIT_FAILURE);  // 终止程序运行
  }
 
  for (i = 0; i < total_counts; i++) {  // 遍历结构体数组
    fprintf(fp, "%c %d\n", counts[i].letter, counts[i].count);  // 将字符和计数值输出到文件中
  }
 
  fclose(fp);  // 关闭输出文件
 
  return 0;
}

参考gpt

 
#include <iostream>
#include <fstream>
#include <string>
#include <algorithm>
#include <vector>
using namespace std;

struct CharCount {
    char c;
    int count;
};

bool cmp(CharCount a, CharCount b) {
    return a.count > b.count;
}

int main() {
    ifstream fin("data1.txt");
    vector<CharCount> charCounts;
    for (char c = 'a'; c <= 'z'; c++) {
        CharCount charCount;
        charCount.c = c;
        charCount.count = 0;
        charCounts.push_back(charCount);
    }
    for (char c = 'A'; c <= 'Z'; c++) {
        CharCount charCount;
        charCount.c = c;
        charCount.count = 0;
        charCounts.push_back(charCount);
    }
    for (char c = '0'; c <= '9'; c++) {
        CharCount charCount;
        charCount.c = c;
        charCount.count = 0;
        charCounts.push_back(charCount);
    }
    char c;
    while (fin.get(c)) {
        for (int i = 0; i < charCounts.size(); i++) {
            if (charCounts[i].c == c) {
                charCounts[i].count++;
                break;
            }
        }
    }
    fin.close();
    sort(charCounts.begin(), charCounts.end(), cmp);
    ofstream fout("data2.txt");
    for (int i = 0; i < charCounts.size(); i++) {
        fout << charCounts[i].c << " " << charCounts[i].count << endl;
    }
    fout.close();
    return 0;
}



下面是一个Java程序,可以实现对文件"data1.txt"中小写英文字母、大写英文字母和数字的出现次数进行统计,并按照出现次数由大到小的顺序将结果写入到文件"data2.txt"中:

import java.io.*;
import java.util.*;

public class Main {
    public static void main(String[] args) {
        // 构建需要统计的字符列表
        List<Character> charsToCount = new ArrayList<>();
        for (char c = 'a'; c <= 'j'; c++) {
            charsToCount.add(c);
        }
        for (char c = 'A'; c <= 'J'; c++) {
            charsToCount.add(c);
        }
        for (char c = '0'; c <= '9'; c++) {
            charsToCount.add(c);
        }

        // 统计字符出现次数
        Map<Character, Integer> charCounts = new HashMap<>();
        try (BufferedReader reader = new BufferedReader(new FileReader("data1.txt"))) {
            int c;
            while ((c = reader.read()) != -1) {
                char ch = (char) c;
                if (charsToCount.contains(ch)) {
                    charCounts.merge(ch, 1, Integer::sum);
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
            return;
        }

        // 按出现次数排序
        List<Map.Entry<Character, Integer>> sortedEntries = new ArrayList<>(charCounts.entrySet());
        Collections.sort(sortedEntries, (e1, e2) -> e2.getValue() - e1.getValue());

        // 将结果写入文件
        try (BufferedWriter writer = new BufferedWriter(new FileWriter("data2.txt"))) {
            for (Map.Entry<Character, Integer> entry : sortedEntries) {
                writer.write(entry.getKey() + ": " + entry.getValue() + "\n");
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

该程序首先构建了需要统计的字符列表,然后使用一个HashMap来统计每个字符在文件中出现的次数。接着,将统计结果按照出现次数排序,并写入到文件"data2.txt"中。

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

int main() {
    char chars[30] = "abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
    int freq[30] = {0};
    
    FILE *fp = fopen("data1.txt", "r");
    char c;
    while ((c = fgetc(fp)) != EOF) {
        for (int i = 0; i < 30; i++) {
            if (c == chars[i]) {
                freq[i]++;
            }
        }
    }
    fclose(fp);
    
    FILE *fp2 = fopen("data2.txt", "w");
    for (int i = 0; i < 30; i++) {
        for (int j = i + 1; j < 30; j++) {
            if (freq[i] < freq[j]) {
                int temp = freq[i];
                freq[i] = freq[j];
                freq[j] = temp;
                
                char tempChar = chars[i];
                chars[i] = chars[j];
                chars[j] = tempChar;
            }
        }
        fprintf(fp2, "%c %d\n", chars[i], freq[i]);
    }
    fclose(fp2);
}