在C中查找一个整数的长度
我想知道如何在C中find一个整数的长度
例如:
- 1 => 1
- 25 => 2
- 12512 => 5
- 0 => 1
等等。
我如何在C中做到这一点?
C:
为什么不把数字的绝对值的10进制取整呢,然后加一个呢? 这适用于不是0的正数和负数,并避免使用任何string转换函数。
log10
, abs
和floor
函数由math.h
提供。 例如:
int nDigits = floor(log10(abs(the_integer))) + 1;
因为log10(0)
根据man 3 log
返回-HUGE_VAL
,所以应该将其包含在一个确保the_integer != 0
的子句中。
此外,如果input是负数,如果您对数字的长度感兴趣(包括其负号),则可能需要将其添加到最终结果中。
Java的:
int nDigits = Math.floor(Math.log10(Math.abs(the_integer))) + 1;
注意在这个方法中涉及的计算的浮点性质可能导致它比一个更直接的方法慢。 有关效率的讨论请参阅康康的回答。
如果你对一个快速而简单的解决scheme感兴趣,以下可能是最快的(这取决于所讨论的数字的概率分布):
int lenHelper(unsigned x) { if(x>=1000000000) return 10; if(x>=100000000) return 9; if(x>=10000000) return 8; if(x>=1000000) return 7; if(x>=100000) return 6; if(x>=10000) return 5; if(x>=1000) return 4; if(x>=100) return 3; if(x>=10) return 2; return 1; } int printLen(int x) { return x<0 ? lenHelper(-x)+1 : lenHelper(x); }
虽然它可能不会赢得最精明的解决scheme的奖励,但是理解并且也是微不足道的,因此执行速度很快。
在使用MSC的Q6600上,我使用下面的循环进行了基准testing:
int res=0; for(int i=-2000000000;i<2000000000;i+=200) res+=printLen(i);
这个解决scheme需要0.062秒,Pete Kirkham使用智能对数方法的第二快的解决scheme需要0.115s – 几乎是两倍。 但是,对于10000或更低的数字,智能日志更快。
以某种清晰度为代价,您可以更可靠地击败智能日志(至less在Q6600上):
int lenHelper(unsigned x) { // this is either a fun exercise in optimization // or it's extremely premature optimization. if(x>=100000) { if(x>=10000000) { if(x>=1000000000) return 10; if(x>=100000000) return 9; return 8; } if(x>=1000000) return 7; return 6; } else { if(x>=1000) { if(x>=10000) return 5; return 4; } else { if(x>=100) return 3; if(x>=10) return 2; return 1; } } }
这个解决scheme在大数量上仍然是0.062s,而对于较小的数字,这个解决scheme会降低到大约0.09s,这两种情况都比智能日志方法更快。 (gcc生成更快的代码;这个解决scheme为0.052,智能日志方法为0.09s)。
int get_int_len (int value){ int l=1; while(value>9){ l++; value/=10; } return l; }
第二个也会为负数工作:
int get_int_len_with_negative_too (int value){ int l=!value; while(value){ l++; value/=10; } return l; }
你可以写一个这样的函数:
unsigned numDigits(const unsigned n) { if (n < 10) return 1; return 1 + numDigits(n / 10); }
n的长度:
length = ( i==0 ) ? 1 : (int)log10(n)+1;
是的,使用sprintf。
int num; scanf("%d",&num); char testing[100]; sprintf(testing,"%d",num); int length = strlen(testing);
或者,您可以使用log10
函数以math方式进行此操作。
int num; scanf("%d",&num); int length; if (num == 0) { length = 1; } else { length = log10(fabs(num)) + 1; if (num < 0) length++; }
最有效的方法可能是使用基于快速对数的方法,类似于那些用于确定整数中最高位的方法。
size_t printed_length ( int32_t x ) { size_t count = x < 0 ? 2 : 1; if ( x < 0 ) x = -x; if ( x >= 100000000 ) { count += 8; x /= 100000000; } if ( x >= 10000 ) { count += 4; x /= 10000; } if ( x >= 100 ) { count += 2; x /= 100; } if ( x >= 10 ) ++count; return count; }
在我的上网本上,这个(可能是过早的)优化花费了2千6百万次。 像zed_0xff这样的迭代分割需要1.6s,像Kangkan这样的recursion分割需要1.8s,并且使用浮点函数(Jordan Lewis的代码)需要6.6s。 使用snprintf需要11.5秒,但会给你snprintf所需的任何格式的大小,而不仅仅是整数。 约旦报告说,他的处理器没有维持时序的顺序,处理器的浮点比我的要快。
最简单的可能是问打印长度snprintf:
#include <stdio.h> size_t printed_length ( int x ) { return snprintf ( NULL, 0, "%d", x ); } int main () { int x[] = { 1, 25, 12512, 0, -15 }; for ( int i = 0; i < sizeof ( x ) / sizeof ( x[0] ); ++i ) printf ( "%d -> %d\n", x[i], printed_length ( x[i] ) ); return 0; }
整数x
的位数等于1 + log10(x)
。 所以你可以这样做:
#include <math.h> #include <stdio.h> int main() { int x; scanf("%d", &x); printf("x has %d digits\n", 1 + (int)log10(x)); }
或者你可以运行一个循环来自己计算数字:做整数除10,直到数字为0:
int numDigits = 0; do { ++numDigits; x = x / 10; } while ( x );
如果第一个解决scheme中的整数是0
,则必须小心地返回1
,并且您可能还想要处理负整数(如果x < 0
则使用-x
)。
正确的snprintf
实现:
int count = snprintf(NULL, 0, "%i", x);
int digits=1; while (x>=10){ x/=10; digits++; } return digits;
非常简单
int main() { int num = 123; char buf[50]; // convert 123 to string [buf] itoa(num, buf, 10); // print our string printf("%s\n", strlen (buf)); return 0; }
sprintf(s, "%d", n); length_of_int = strlen(s);
你可以使用这个 –
(DATA_TYPE)LOG10(variables名)+1
例如:
len =(int)log10(number)+1;
保持十分之一,直到你得到零,然后只输出分割数。
int intLen(int x) { if(!x) return 1; int i; for(i=0; x!=0; ++i) { x /= 10; } return i; }
我认为我得到了最有效的方式来find一个整数的长度,它是一个非常简单和优雅的方式:
int PEMath::LengthOfNum(int Num) { int count = 1; //count starts at one because its the minumum amount of digits posible if (Num < 0) { Num *= (-1); } for(int i = 10; i <= Num; i*=10) { count++; } return count; // this loop will loop until the number "i" is bigger then "Num" // if "i" is less then "Num" multiply "i" by 10 and increase count // when the loop ends the number of count is the length of "Num". }
在我看来,最简单的解决scheme是:
int length , n; printf("Enter a number: "); scanf("%d", &n); length = 0; while (n > 0) { n = n / 10; length++; } printf("Length of the number: %d", length);
我的方式:
只要数字不能被10整除:
u8 NumberOfDigits(u32 number) { u8 i = 1; while (number /= 10) i++; return i; }
与其他命题相比,我不知道有多快。
int intlen(int integer){ int a; for(a = 1; integer /= 10; a++); return a; }