我可以包含包含随机10位数字的字符串,例如
"abcgfg1234567890gfggf"
或
"fgfghgh3215556890ddf"
等
基本上是字符串中10个数字加字符的任意组合,所以我需要检查字符串以确定是否存在10位数字。我使用strspn但它返回0
char str_in[] = "abcgfg1234567890gfggf";
char cset[] = "1234567890";
int result;
result = strspn(str_in, cset); // returns 0 need it to return 10
以下代码返回0而不是10的事实凸显了该问题。我之前问过这个问题,但大多数回复是针对已知的10位数字进行检查。在我的情况下,数字将是随机的。还有比strspn
更好的方法吗?
答案 0 :(得分:3)
它返回0,因为字符串的开头没有数字。
strspn()函数计算的长度(以字节为单位) s的初始段,完全由accept中的字节组成。
您需要跳过非数字 - strcspn
- 然后在字符串+该偏移量上调用strspn
。你可以尝试:
/* Count chars to skip. */
skip = strcspn(str_in, cset);
/* Measure all-digit portion. */
length = strspn(str_in + skip, cset)
我应该提到这必须在一个循环中完成。例如,如果您的字符串为"abcd123abcd1234567890"
,则第一个strspn
只会匹配3个字符,您需要进一步查看。
答案 1 :(得分:1)
只需使用sscanf()
:
unsigned long long value;
const char *str_in = "abcgfg1234567890gfggf";
if(sscanf(str_in, "%*[^0-9]%uL", &value) == 1)
{
if(value >= 1000000000ull) /* Check that it's 10 digits. */
{
/* do magic here */
}
}
以上假设unsigned long long
足够大以容纳10位十进制数,实际上这意味着它假设是64位类型。
%*[^0-9]
转换说明符告诉sscanf()
忽略一堆非(十进制)数字的初始字符,然后直接转换无符号长long(%uL
)。尾随字符将被忽略。
答案 2 :(得分:0)
替代使用sscanf()
(@unwind的明显变化)
const char *str_in = "abcgfg0123456789gfggf";
int n1 = 0;
int n2 = 0;
// %*[^0-9] Scan any non-digits. Do not store result.
// %n Store number of characters read so far.
// %*[0-9] Scan digits. Do not store result.
sscanf(str_in, "%*[^0-9]%n%*[0-9]%n", &n1, &n2);
if (n2 == 0) return 0;
return n2 - n1;
计算前导0
个字符作为数字计数的一部分。
是否应该避免sscanf()
char str_in[] = "abcgfg1234567890gfggf";
const char *p1 = str_in;
while (*p1 && !isdigit(*p1)) p1++;
const char *p2 = p1;
while (isdigit(*p2)) p2++;
result = p2 - p1;
答案 3 :(得分:0)
使用正则表达式怎么样?
#include <stdio.h>
#include <stdlib.h>
#include <regex.h>
int
main(int argc, char **argv)
{
char str_in[] = "abcgfg1234567890gfggf";
int result = 0;
const char *pattern = "[0-9]{10}";
regex_t re;
char msg[256];
if (regcomp(&re, pattern, REG_EXTENDED|REG_NOSUB) != 0) {
perror("regcomp");
return(EXIT_FAILURE);
}
result = regexec(&re, str_in, (size_t)0, NULL, 0);
regfree(&re);
if (!result) {
printf("Regex got a match.\n");
} else if (result == REG_NOMATCH) {
printf("Regex got no match.\n");
} else {
regerror(result, &re, msg, sizeof(msg));
fprintf(stderr, "Regex match failed: %s\n", msg);
return(EXIT_FAILURE);
}
return(EXIT_SUCCESS);
}
答案 4 :(得分:0)
strspn
似乎很方便,但您必须将其包含在循环中并多次搜索。鉴于具体要求,最简单的方法可能就是制作自己的自定义功能。
int find_digits (const char* str, int n);
/* Searches [str] for a sequence of [n] adjacent digits.
Returns the index of the first valid substring containing such a sequence,
otherwise returns -1.
*/
#include <ctype.h>
int find_digits (const char* str, int n)
{
int result = -1;
int substr_len = 0;
int i = 0;
for(int i=0; str[i] != '\0'; i++)
{
if(isdigit(str[i]))
{
substr_len++;
}
else
{
substr_len=0;
}
if(substr_len == n)
{
result = i;
break;
}
}
return result;
}
(我刚刚在这里攻击了这个,现在没有经过测试,但是你明白了。这很可能是这个任务的最快算法,也就是说,如果性能很重要的话)
答案 5 :(得分:0)
在字符串中测试一套“0123456789”你可以做类似的事情:
int main()
{
char str_in[] = "abcgfg1234567890gfggf";
char cset[] = "1234567890";
int result;
int i;
int f;
i = 0;
f = 0;
while (str_in[i])
{
if (str_in[i] == cset[f])
{
f++;
if(f == strlen(cset))
return (f);
}
else
f = 0;
i++;
}
}