arrays - 有人可以帮我微调这段代码中的 **else if** 语句吗?
问题描述
我正在尝试编写一个代码来检查用户输入的密码是否符合密码格式,例如“ L$$222ee
”(第一个大写字母,后跟两个特殊字符,后跟三位数字,最后是两个小写字母)。我的代码运行良好;我只想完善else if语句。这是代码:
#include<stdio.h>
#include<string.h>
#include<ctype.h>
//format required: L$$222ee
int main(){
char pass[8];
printf("Enter password:\n");
gets(pass);
if(strlen(pass)<8){
printf("Password is too short...!!!\n");
}
else if(isupper(pass[0]) && ((!isalpha(pass[1]) && !isalpha(pass[2])) && !isdigit(pass[1]) && !isdigit(pass[2]))
&& (isdigit(pass[3]) && isdigit(pass[4]) && isdigit(pass[5])) && (isalpha(pass[6])
&& isalpha(pass[7]))){
printf("Password is compliant");
}
else{
printf("Error: password is not compliant with the format!!!\n");
}
return 0;
}
解决方案
由于所有这些 ctype.h 函数都具有相同的格式int func (int)
,您可以利用它来创建对应于所有需要完成的检查的查找表。查找表的优点是它比相当不可读的&&
.
首先创建一个与 ctype 函数相同的函数 typedef:typedef int ctype_func_t (int);
然后制作一个在查找表中使用的结构。存储字符串索引、结果的真假条件以及函数本身:
typedef struct
{
size_t index;
bool cond;
ctype_func_t* check_func;
} check_t;
然后可以创建一个查找表:
const check_t fmt_check [] =
{
{0, true, isupper },
{1, false, isalpha },
{2, false, isalpha },
{1, false, isdigit },
{2, false, isdigit },
{3, true, isdigit },
{4, true, isdigit },
{5, true, isdigit },
{6, true, isalpha },
{7, true, isalpha },
};
顺序不重要,随意添加或删除格式要求。完整的函数如下所示:
int ispwcorrect (const char pw[8])
{
typedef int ctype_func_t (int);
typedef struct
{
size_t index;
bool cond;
ctype_func_t* check_func;
} check_t;
const check_t fmt_check [] =
{
{0, true, isupper },
{1, false, isalpha },
{2, false, isalpha },
{1, false, isdigit },
{2, false, isdigit },
{3, true, isdigit },
{4, true, isdigit },
{5, true, isdigit },
{6, true, isalpha },
{7, true, isalpha },
};
for(size_t i=0; i<sizeof fmt_check/sizeof *fmt_check; i++)
{
unsigned char ch = pw[ fmt_check[i].index ];
if((bool)fmt_check[i].check_func(ch) != fmt_check[i].cond)
{
return false;
}
}
return true;
}
这应该是不言自明的,它通过循环中的函数指针调用 ctype 函数,并以特定的字符串索引字符作为参数。然后检查真/假条件。一旦出现不匹配,检查就会停止。
调用每个 ctype 函数后的强制转换bool
是必要的,因为它们返回零或非负数int
。因此,将 abool
与这样的非零进行比较是int
行不通的,因为 == 会将bool
参数提升为 a int
。
这应该大大优于正则表达式,但会比原始 if-else 稍慢。
与您的问题无关,您在这里也有一个严重的错误:char pass[8];
. 空终止符没有空间,所以你不能存储"L$$222ee"
在里面pass
。
推荐阅读
- javascript - 获取点击次数并使用 jquery 调用单个 ajax 调用
- ios - React Native Gesture Reponder 在混合应用程序中
- java - Defining Entities to connect mysql database to a java project
- java - Java 8 将 n 个大小的集合划分为 m 个未知大小的列表
- javascript - Display Clock with Angular 6 and RxJs 6
- python - While loop in python showing value of next word while reading a file
- php - Get the Page ID when the displayed product as has a different ID in Woocommerce
- ethereum - Send ERC-20 token from another contract
- android - 如何使android对象动画师响应?
- machine-learning - 如何判断模型是否过拟合