【问题标题】:Password Checker in CC中的密码检查器
【发布时间】:2016-08-12 10:42:57
【问题描述】:

我想构建一个简单的程序来检查用户输入的密码是否包含至少一个大写字母、一个数字和一个符号。然后如果真打印“这是一个强密码”。 但是,当我开始测试它时,如果我输入像 SS2 这样的 pass,它会被视为强密码...

int issymbol(int password) {
    if (password >= 33 && password <= 47) return 1;
    else if (password >= 58 && password <= 64) return 1;
    else if (password >= 91 && password <= 96) return 1;
    else if (password >= 123 && password <= 126) return 1;
    else return 0;
}

int main()
{
    char password[7];
    int i;
    int u, d, s;        // u - uppercase character
                        // d - digit
    u = d = s = 0;      // s - symbol

    scanf("%s", password);

    for(i = 0; i < 7; i++) {
        if ( isupper(password[i]) && (u == 0) )
            u++;
        if ( isdigit(password[i]) && (d == 0) )
            d++;
        if ( issymbol(password[i]) && (s == 0) )   // Checks if password[i] is a symbol
            s++;
        if ( (u + d + s) >= 3) {
            printf("Your password is strong!\n");
            break;
        }
    }

    if ( (u + d + s) < 3)  printf("Your password is weak:(\n");

    return 0;
}

欢迎任何改进它的想法。

【问题讨论】:

  • 又是一个了解调试器是多么出色的工具的绝佳机会。
  • 结束循环条件错误,它必须取决于密码长度。
  • scanf("%s", password); --> scanf("%6s", password);
  • 当您输入 SS2 时,它的得分为 3,然后中断。如果你不喜欢这样,那就改变你的逻辑。
  • 是的,通过使用@Bathsheba 逻辑它可以工作。

标签: c


【解决方案1】:

你不是说if (u &gt;= 1 &amp;&amp; d &gt;= 1 &amp;&amp; s &gt;= 1) 是一个强密码吗?然后你就可以放下写&amp;&amp; (u == 0)等的乏味了。

您当前的测试只是字符数。

另外,你的代码很脆弱:如果用户输入超过 6 个字符,事情就会出错:记得为 nul 终止符 \0 留出一个字节。作为绝对最低限度,写scanf("%6s", password); 并将循环运行到第一个\0 而不是7。有关更多详细信息,请参阅How to prevent scanf causing a buffer overflow in C?

【讨论】:

  • 不应该是&gt;= 1,而不是&gt; 1吗?
  • @Barmar:是的。修正。我们将联合发布。
  • 您也可以将其简化为if (u &amp;&amp; d &amp;&amp; s)。弱测试是if(!u || !d || !s)
  • @Barmar:确实可以,但我只会对unsigned 类型这样做。我知道有点强迫症。
  • 嗯,这些变量可能应该是无符号的。每种类型的字符数不能为负数。
【解决方案2】:
int issymbol(int password)

您的变量password 应该是char 类型来检查符号而不是int

编辑:

scanf("%s", password);

总是在%s之前加空格,比如

scanf(" %s", password)

这将终止之前的所有\n

【讨论】:

  • 我是否也应该输入“%6s”。
  • 不:密码是用户输入的第一件事。前导空格是一种粗略但偶尔有效的方式,用于传递用户类型返回时发送到输入缓冲区的换行符。
【解决方案3】:

问题是您检查的字符多于输入的字符。如果您键入 SS7,则只有 3 个字符要检查,但您的 for 循环会检查 password 中的所有 7 字符。 password[3]后面的字符会被初始化,可能包含符合要求的字符。

将循环改为:

for (i = 0; password[i]; i++) {

当它到达字符串中的终止空字符时,这将停止。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2014-11-08
    • 1970-01-01
    • 1970-01-01
    • 2015-08-05
    • 1970-01-01
    • 1970-01-01
    • 2021-01-30
    • 1970-01-01
    相关资源
    最近更新 更多