ProgrammingThis forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
Long story short, my issue is that I'm having a hard time trying to get the number of digits in a uint64_t variable. The reason I'm using this is I want to make sure I get x amount of digits inside of a variable before I use it, but since the higher the digits, the better the program is.
I currently use the following code, and it works, but my loop will never exit because the length is always 0:
Code:
/**
* numbdigits()
* number: The number to evaluate [in]
*
* Returns the number of digits found in a number.
**/
uint64_t numdigits(uint64_t number){
uint64_t tmp = number;
uint64_t i = 0;
if(number < 0)
tmp = -tmp;
while(tmp){
tmp /= 10;
i++;
}
return i;
}
Here's my code with the loop (that calls numdigits()):
Anyone know what's going on? :/ getrand() returns a uint64_t as well (and works). The only way the while() loop ends without my intervention is if I do curd += numdigits(val) instead...but, that gives a false value as well.
I think numdigits is correct (although checking if number is negative is useless because unsigned values can't be negative). What are you passing into sized_num? Do you realize that the max number of digits you can get is 19 = floor(log10(2^64)) 20 = ceiling(log10(2^64))?
Last edited by ntubski; 07-07-2011 at 09:09 PM.
Reason: mixed up the digit formula
You did not specify what parameter you gave to sized_num, nor did you tell us what getrand() returns.
Assuming getrand() picks one of its parameters at random, and returns it, then val will be between 1 and 36 every single time, and curd either 1 or 2. So, if you called sized_num(2) (or with any parameter larger than 2), the loop will obviously never end.
Also, uint64_t is a two's complement unsigned 64-bit integer, and therefore between 0 and 18446744073709551615 (inclusive). Exactly, not more, nor less. It can never be negative. Personally, I'd do a four-level comparison tree (since you only have 21 possible results -- 0, or 1 to 20 digits), in which case any input only takes four comparisons against fixed values to arrive at the correct result. Your code will need 21 comparisons in the function total, of course; just arranged as a binary tree.
What are you passing into sized_num? Do you realize that the max number of digits you can get is 19 = floor(log10(2^64))?
The number of digits function is actually ceil(log10(input)), as the OP returns 0 for zero input. If you count zero input also as one digit, then the function is 1+floor(log10(input)). In both cases the maximum number of digits for a 64-bit unsigned integer is 20, not 19.
What I'm passing to sized_num() is 300 (as I want 300 digits...which according to Nominal Animal, this isn't possible). This would explain, also, why it always return 19 or 20.
getrand() was a CMWC random-number generator that also returned a uint64_t, but I've since switched to a Mersenne Twister 64-bit random number generator (uint64_t).
Basically what I'm doing is trying to write a Dillie-Hellman Key Exchange system, and I'm trying to implement what can be best done as a purely random number generator for both the prime P, and secret of the user (so I can generate a secret key).
Perhaps I overly complicated this matter? I just didn't want to use srand()/rand(), and figured 64-bit integers would provide better encryption than a 32-bit integer would.
Perhaps I overly complicated this matter? I just didn't want to use srand()/rand(), and figured 64-bit integers would provide better encryption than a 32-bit integer would.
More like over simplifying: you need, at a minimum, 512-bit integers for a reasonable level of security (300 decimal digits is almost 1000 bits). You can use a library like gmp to get large integers, or, since I assume you are doing this for educational purposes, you may want to roll your own.
More like over simplifying: you need, at a minimum, 512-bit integers for a reasonable level of security (300 decimal digits is almost 1000 bits). You can use a library like gmp to get large integers, or, since I assume you are doing this for educational purposes, you may want to roll your own.
Well, I'm trying to stay away from third-party libraries as much as possible, and am trying to roll my own...which is where I'm having issues it seems.
I've decided to go with a third-party library to make this task so much easier.
I know GMP supports integers bigger than 64, but is it possible with GLib as well? I can't find any information on how to do it, but there's nothing saying yes or no to this.
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.