首页 文章

初学C程序 - 如何从anagram程序中的循环返回必要的输出?

提问于
浏览
0

感谢您查看我的问题!

我正在尝试从C中的教科书示例练习中创建一个工作程序(我还是初学者,我正在通过书籍/笔记学习),这将确定用户输入的两个字符串是否为字谜(无论是否为案例或间距) . 为什么我的程序正在编译,但没有超过第一个getString提示符以允许用户输入第二个字符串?以下是练习的目标,以及到目前为止我写的代码(在底部) .

Algorithm 读取第一个字符串,然后编写一个循环,使用26个整数的数组来计算每个字母被看到的次数 . 读取第二个字符串,这次减少int数组中每个字母的计数 . 如果int数组中的每个元素都为0,则字符串为字符串 . 忽略任何非字母的字符 . 将大写字母视为与小写字母相同 . 有关这方面的帮助如下 .

Functions required 您需要使用以下功能 . 您必须设计适当的参数和返回类型 . 如果它们使您的程序更简单,更清晰,您还可以添加其他功能 .

main() 声明变量,然后调用下面描述的函数来解决问题 .

initialize() 在读取第一个字符串之前清除所有char和int数组的内容 . (将char数组中的每个元素设置为空字符'\ 0' . )

getString() 从输入中提示并读取字符串 . 在执行此操作时,请调用标准库函数gets() . 函数原型是:char * gets(char s []);将下一个输入行读入字符串s;它用'\ 0'替换终止换行符 . 它返回s,如果发生文件结束或错误,则返回NULL .

setLetters() 循环第一个字符串中的每个字符,并更新int数组中该字母的计数 . 从这里调用以下标准库函数 . 函数原型是:

如果字符c是小写或大写字母,则 int isalpha(char c) 返回非零(true)

char tolower(char c) 如果字符c是大写字母,则返回相应的小写字母;否则它返回c

checkLetters() 循环第二个字符串中的每个字符,并从int数组中该字母的计数中减去1 . 与setLetters()非常相似 .

isZero() 遍历int数组 . 如果每个元素都为0,则返回TRUE,否则返回FALSE .

This is the code I've written so far, it compiles but doesn't get to the second string:

#include <stdio.h>
#include <ctype.h>
#define ABC 26


/* lab5.c: Compares user input to determine if they are anagrams */
char initialize(char s1[], char s2[], int count[]);
char getString(char s[]);
char *gets(char s[]);
int setLetters(char s1[], int count[]);
int checkLetters(char s2[], int count[]);
int isZero(int count[]);

int main() {

    char string1[100];
    char string2[100];
    int count1[ABC] = {0};

    initialize(string1, string2, count1);

    getString(string1);
    setLetters(string1, count1);
    getString(string2);
    checkLetters(string2, count1);

    isZero(count1);

}
char initialize(char s1[], char s2[], int count[]) {
    int i;

    for (i = 0; s1[i] != '\0'; i++) {
        s1[i] = '\0';
        s2[i] = '\0';
        count[i] = 0;
    }
}
int setLetters(char s1[], int *count[]) {
    int i = 0;

    while (s1[i] != '\0') {
      if (isalpha(s1[i])) {
        count[tolower(s1[i]) - 'a']++;
        i++;
      }
   }
   return count;
}
int checkLetters(char s2[], int count[]) {
    int i;

    while (s2[i] != '\0') {
      if (isalpha(s2[i])) {
        count[tolower(s2[i]) - 'a']--;
        i++;
      }
   }
}
char getString(char s[]) {

    printf("Enter the string: ");
    gets(s);
}
int isZero(int count[]) {
    int i;
    int x = 0;

    for (i = 0; i < ABC; i++) {
        if (count[i] != 0)
            x = 1;
    }
    if (x == 1) {
        printf("Not Anagram");
    }
    else {
        printf("Anagram");
    }
}

输出:

Enter the string: mattress
Enter the string: smartest
Not Anagram

......这并不是正确的输出 . :P

1 回答

  • 1

    我道歉,我打算昨晚发布一个例子来替换你的 getString 功能 . 下面是一个函数 fgetsinput 的简单示例,您可以使用 stdinstdin 获取输入,这将极大地提高代码的安全性/漏洞性 . 注意当使用在堆栈上静态创建的存储时, #define 是一个常量,表示要读取的最大输入行(或字符串) . 下面,要读取的最大字符串大小是一个常量 MAXS ,最初定义为 256 . 您可以根据需要进行调整 . 看到的正常值范围通常在 1282048 之间

    同样 note 通过将存储字符串初始化为全零(null),您将使用 null-terminating 字符填充字符串,确保您的输入将 alwaysnull-terminated ,除非您覆盖 MAXS-1 处的最后一个空值:

    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    
    #define MAXS 256
    
    char *fgetsinput (char *s)
    {
        fgets (s, MAXS - 1, stdin);     /* read string from stdin   */
    
        size_t len = strlen (s);        /* calculate length         */
    
        if (s[len-1] == '\n')           /* if last char is newline  */
            s[len-1] = 0;               /* set to null-terminator   */
    
        return s;                       /* return adds flexibility  */
    }
    
    int main (void) {
    
        char line[MAXS] = {0};                  /* initialize to zero (null)    */
    
        while (strcmp (line, "quit") != 0)
        {
            printf ("\n enter a string : ");
            fgetsinput (line);                  /* return not used in this call */
            printf (" string in line : %s\n", line);
        }
    
        printf ("\n enter a string to assign to pointer  : ");
    
        char *p = fgetsinput (line);            /* return assinged to pointer   */
        printf (" What is the value pointed to by 'p'? : %s\n\n", p);
    
        return 0;
    }
    

    output:

    $ ./bin/getinputex
    
      enter a string : A string for fgets to read.
      string in line : A string for fgets to read.
    
      enter a string : quit
      string in line : quit
    
      enter a string to assign to pointer  : A string for fgets to read and assign.
      What is the value pointed to by 'p'? : A string for fgets to read and assign.
    

    通过将文件描述符作为函数的参数之一传递,可以轻松扩展该函数以从任何文件流中读取 . (例如 char *fgetsinput (char *s, FILE *fp) ) . 然后,您可以使用 fp 替换函数中的 stdin ,并从任何打开的文件流中读取 .

相关问题