如何获得与要排序的出现次数相对应的字母?

时间:2014-03-01 18:02:59

标签: c loops pointers bubble-sort

我在Ubuntu中使用GCC制作一个小型ANSI C应用程序。程序查找字符串中每个字母的出现值,然后根据出现的次数按降序对它们进行排序。

我的main.c文件:

/*
* preprocessor directives
*/
#include "bubbleSort.h"

/*
* global variables
*/
char Ar[] = "All Gaul is divided into three parts, one of which the Belgae inhabit, the Aquitani another, those who in their own language are called Celts, in our Gauls, the third. All these differ from each other in language, customs and laws. The river Garonne separates the Gauls from the Aquitani; the Marne and the Seine separate them from the Belgae. Of all these, the Belgae are the bravest, because they are furthest from the civilization and refinement of [our] Province, and merchants least frequently resort to them, and import those things which tend to effeminate the mind; and they are the nearest to the Germans, who dwell beyond the Rhine , with whom they are continually waging war; for which reason the Helvetii also surpass the rest of the Gauls in valor, as they contend with the Germans in almost daily battles, when they either repel them from their own territories, or themselves wage war on their frontiers. One part of these, which it has been said that the Gauls occupy, takes its beginning at the river Rhone ; it is bounded by the river Garonne, the ocean, and the territories of the Belgae; it borders, too, on the side of the Sequani and the Helvetii, upon the river Rhine , and stretches toward the north. From 'Caesar's Conquest of Gaul', Translator. W. A. McDevitte. Translator. W. S. Bohn. 1st Edition. New York. Harper & Brothers. 1869. Harper's New Classical Library. Published under creative commons and available at http://www.perseus.tufts.edu/hopper/text?doc=Perseus:text:1999.02.0001";

/*
* main function
*/
int main(void) {
    /*array to hold count of each letter in alphabet*/
    int ABStats[ALPHABET_SIZE] = { 0 };

    /*array to hold letters of alphabet*/
    char chAlphabet[ALPHABET_SIZE] = {'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'};

    /*pointers for use in finding frequency of characters*/
    char *pAr = Ar;
    char *pAlphabet = chAlphabet;
    int *pABStats = ABStats;

    GetFrequency(pAr, pABStats); /*get the frequency of each letter*/
    DisplayVHist(pABStats, ALPHABET_SIZE); /*display the frequency of each letter*/

    int i, j;
    for (i = ALPHABET_SIZE-1; i >= 0; i--) {
        for (j = 0; j < i; j++) {
            if (*(pABStats+j) < *(pABStats+j+1)) {
                Swap(pABStats+j, pABStats+j+1);
            }
        }
    }

    DisplayVHist(pABStats, ALPHABET_SIZE); /*display the frequency of each letter*/

    return EXIT_SUCCESS; /*return zero*/
}

我的bubbleSort.c文件:

/*
* preprocessor directives
*/
#include "bubbleSort.h"

/*
* functions
*/
int GetFrequency(char *pAr, int *pABStats) {
    int chNum = 0;
    for (; *pAr != '\0'; pAr++) { /*check if at the end of the array*/
        char ch = *pAr; /*store current letter as a char*/
        if (isalpha(ch)) /*if character is a letter*/
            chNum = (toupper(ch) - 'A'); /*return ascii code of specified letter*/
        pABStats[chNum]++; /*store ascii value in array and increment array*/
    }
    return chNum;
}

void DisplayVHist(int *pABStats, int size) {
    int i, j;
    const float lengthAr = strlen(Ar); /*store length of array as a float*/
    for (i = 0; i < size; i++) { /*for each letter in the alphabet*/
        float chPercent = 100 * (*pABStats / lengthAr); /*calculate percentage*/
        printf("'%c' --> %6.3f percent --> %3d occurances --> ", (i + 'A'), chPercent, *pABStats);
        for (j = 0; j < (*pABStats / 2); j++) { /*for every two values being pointed to by pointer*/
            printf("%c",'*'); /*print asterisk*/
        }
        printf("\n");
        pABStats++;
    }
}

void Swap(int *pA, int *pB) {
    int temp;
    temp = *pA;
    *pA = *pB;
    *pB = temp;
}

我的bubbleSort.h文件:

/*
* preprocessor directives
*/
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>

#define ALPHABET_SIZE 26

/*
* global variables
*/
extern char Ar[];

/*
* function prototypes
*/
int GetFrequency(char*, int*);
void DisplayVHist(int*, int);
void Swap(int*, int*);

它目前所做的是按降序对发生值进行排序,这是我想要的,但是当我显示结果时,'A'将具有最高值,这将是错误的。我希望以与出现次数相同的方式对字母进行排序,以便出现次数最多的字母(即“E”)将出现在列表的顶部及其出现位置。我为此创建了一个名为chAlphabet的char数组。

我需要为此应用程序使用指针,即使它可能不是最有效的方法来使用此应用程序。我还需要在bubbleSort.c中使用Sort()函数进行排序。

任何帮助将不胜感激。我是C编程的新手。谢谢。

1 个答案:

答案 0 :(得分:1)

好的,所以已经可以交换pABStats,每个字母的统计数据,现在你需要做的就是交换字母表。要做到这一点,你需要一个数组,就像pABStats一样,对于Alphabet,幸运的是你已经有了chAlphabet

然后你需要一个交换的函数,就像你拥有的Swap函数一样,但这次它应该取char *个参数,例如,像这样:

//in bubbleSort.c

void SwapAlphabet( char *pA, char *pB ) {
    char temp;
    temp = *pA;
    *pA = *pB;
    *pB = temp;
}

只需按照调用Swap函数的方式调用此方法,以及之后或之前的调用方式:

//inside the second for in main in main.c

if ( blabla ) {
    Swap( ... );
    SwapAlphabet( chAlphabet + j, chAlphabet + j + 1 ); // <-- added this
}

最后,为打印函数引入一个新的第三个参数DisplayVHist,它将chAlphabet保留main

//in bubbleSort.c
void DisplayVHist( ..., ..., char *chAlphabet ) { ... }

//and in bubbleSort.h
void DisplayVHist( ..., ..., char* );

chAlphabet调用函数main作为第三个参数:

//towards the end in main in main.c
DisplayVHist( ..., ..., chAlphabet );
我之前撒了谎,但这将是最后一部分。更改(i + 'A')printf内的DisplayVHist,以执行您已为pABStats执行的操作。它应该是这样的:

//inside the DisplayVHist in bubbleSort.c

printf( "...", *chAlphabet, chPercent, *pABStats );
...
chAlphabet++;

这应该是它,除非我错过了我在这里做过的编辑。无论何时需要进一步澄清,请随时提出任何问题。