Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.c > #167560
| From | Tim Rentsch <tr.17687@z991.linuxsc.com> |
|---|---|
| Newsgroups | comp.lang.c |
| Subject | Re: Beginner....Decimal/Octal converter help |
| Date | 2022-09-09 09:16 -0700 |
| Organization | A noiseless patient Spider |
| Message-ID | <86leqsr091.fsf@linuxsc.com> (permalink) |
| References | <8ffd982c-2e82-4caa-9256-ec17be2efe56n@googlegroups.com> |
ManyBeers <markzuffi@yahoo.com> writes:
> Hello I am teaching myself C and I need some help with a problem.
> After a search for dec/oct convert I found this code:
>
> [..code..]
I would like to offer a different kind of answer to your
questions. First a suggestion: for this kind of problem I think
you will find it helpful to use unsigned types exclusively. In
the code below we will need (besides a plain 'unsigned' here and
there) two types, one for 8-bit values and one for 32-bit values:
typedef unsigned char UC;
typedef unsigned int UI;
Next we need to talk about what you're doing, which is base
conversion. That is to say, you have a number in one base, and
you want to convert it to a different base. Properly speaking
the word digit usually means a decimal digit, or a value between
0 and 9 inclusive. However, we are working in various bases, so
I will use "digit" to mean a value in the appropriate range for
the base in question. Now, what is a number in base B? It is a
sequence of "digits" in base B, that is, values between 0 and
B-1. A natural way to represent a number in base B is as an
array of elements for the "digits", where each element can hold a
value in the relevant range. For bases up to 256, these elements
can be of type UC - an unsigned character can hold all values
between 0 and 255, so it can hold all values between 0 and 9 (for
decimal), or all values between 0 and 7 (for octal), or all
values between 0 and 15 (for hexadecimal), etc. Here are some
sample holders of numbers in different bases:
UC decimal_197[] = { 1, 9, 7 };
UC octal_1777[] = { 1, 7, 7, 7 };
UC hex_FF[] = { 15, 15 };
(Slight digression: Notice that there is nothing marking the
"end" of a number. To use these variables we need to know how
many "digits" are held, which is the same as the number of
elements in each array. There is a well-known idiom in C that
computes what this is, given the variable name. That idiom is
typically written as a macro, as for example
#define NUMBER_OF( a ) (sizeof (a) / sizeof *(a))
We will see uses of this macro in the code below.)
Okay, so we have some array variables holding numbers in
different bases. To make use of these numbers we need to convert
them into C's native numeric type, which here means the type UI.
What is a value of type UI? Because a UI has 32 bits, a variable
of type UI is a single "digit" in base 2**32, or 4294967296.
Here is a function to convert a base-10 number to a UI, which is
to say to a base-4294967296 number:
UI
base_10_to_base_4294967296( UC digits[], unsigned n ){
unsigned i;
UI r = 0;
for( i = 0; i < n; i++ ){
r = r * 10 + digits[i];
}
return r;
}
Code to convert a base-8 number to a UI is almost identical:
UI
base_8_to_base_4294967296( UC digits[], unsigned n ){
unsigned i;
UI r = 0;
for( i = 0; i < n; i++ ){
r = r * 8 + digits[i];
}
return r;
}
And it's easy to see how to generalize these functions into a
single function that will handle any base between 2 and 256:
UI
base_b_to_base_4294967296( unsigned b, UC digits[], unsigned n ){
unsigned i;
UI r = 0;
for( i = 0; i < n; i++ ){
r = r * b + digits[i];
}
return r;
}
Having written these, we are now ready to write a simple test
driver:
#include <stdio.h>
#define NUMBER_OF( a ) (sizeof (a) / sizeof *(a))
int
main(){
UC decimal_197[] = { 1, 9, 7 };
UC octal_1777[] = { 1, 7, 7, 7 };
UC hex_FF[] = { 15, 15 };
unsigned decimal_197_digits = NUMBER_OF( decimal_197 );
unsigned octal_1777_digits = NUMBER_OF( octal_1777 );
unsigned hex_FF_digits = NUMBER_OF( hex_FF );
UI u197d = base_10_to_base_4294967296( decimal_197, decimal_197_digits );
UI u1777o = base_8_to_base_4294967296( octal_1777, octal_1777_digits );
UI uFFh = base_b_to_base_4294967296( 16, hex_FF, hex_FF_digits );
printf( " u197d is %7u decimal\n", u197d );
printf( "u1777o is %7u decimal\n", u1777o );
printf( " uFFh is %7u decimal\n", uFFh );
printf( "\n" );
printf( " u197d is %7o octal\n", u197d );
printf( "u1777o is %7o octal\n", u1777o );
printf( " uFFh is %7o octal\n", uFFh );
printf( "\n" );
printf( " u197d is %7x hexidecimal\n", u197d );
printf( "u1777o is %7x hexidecimal\n", u1777o );
printf( " uFFh is %7x hexidecimal\n", uFFh );
printf( "\n" );
return 0;
}
Notice that the UI variables are not inherently either decimal,
octal, or hexadecimal. The printed values come out as decimal,
octal, or hexadecimal, by virtue of what conversion specifier
(u, o, or x) is used in the printf() format string. You see
that?
Now for the next step. The code above allows conversion from an
arbitrary base (up to 256) to the base of C's native unsigned
type. What we're looking for is a function that goes the other
direction: from the base of C's native unsigned type to an array
of "digits" in a smaller base. This function needs different
interface. In particular, it should take a parameter that is a
pointer to an array of UC, and should return a count of the
number of digits in the result. Here is our first try:
unsigned
base_4294967296_to_base_b_X( UI value, unsigned b, UC out[] ){
UI v = value;
unsigned k = 0;
do {
out[k] = v % b;
k++;
} while( v /= b, v != 0 );
return k;
}
This function sort of works, but it has a problem: the generated
"digits" are backwards! An annoying artifact of conversions like
this is they really want to start at "the wrong end".
There are various ways to correct this problem, but probably the
easiest to explain is to put digits into a temporary array, and
then copy them in reverse order to the out[] array. And so,
unsigned
base_4294967296_to_base_b( UI value, unsigned b, UC out[] ){
UI v = value;
unsigned k = 0;
UC digits[100];
unsigned i;
do {
digits[k] = v % b;
k++;
} while( v /= b, v != 0 );
for( i = 0; i < k; i++ ){
out[ i ] = digits[ k-1-i ];
}
return k;
}
Please take a look over the above code and explanations, and see
if things make more sense now. Are there any questions you have?
One more note, on a more advanced topic. In the code above we
have limited the base-4294967296 numbers to only one UI, which is
to say limited those numbers to only one "digit". If we want to
represent very large numbers, we can have an _array_ of UI, with
each element of the array holding a single base-4294967296 digit.
Doing that is possible of course, but it's a lot harder, so while
you're still learning C you might want to stick with the simpler
cases explained above.
Back to comp.lang.c | Previous | Next — Previous in thread | Next in thread | Find similar | Unroll thread
Beginner....Decimal/Octal converter help ManyBeers <markzuffi@yahoo.com> - 2022-09-08 11:34 -0700
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-08 11:56 -0700
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-08 20:19 +0100
Re: Beginner....Decimal/Octal converter help Barry Schwarz <schwarzb@delq.com> - 2022-09-08 12:34 -0700
Re: Beginner....Decimal/Octal converter help Joe Pfeiffer <pfeiffer@cs.nmsu.edu> - 2022-09-08 20:38 -0600
Re: Beginner....Decimal/Octal converter help Öö Tiib <ootiib@hot.ee> - 2022-09-09 03:22 -0700
Re: Beginner....Decimal/Octal converter help gazelle@shell.xmission.com (Kenny McCormack) - 2022-09-09 13:30 +0000
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-09 09:16 -0700
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-09 19:06 +0000
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-10 11:58 +0200
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-10 11:37 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-10 13:05 +0200
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-10 14:42 +0000
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-10 16:10 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-10 18:14 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-10 12:54 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-10 16:22 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-10 19:03 +0100
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-10 19:30 +0100
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-10 19:47 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-11 14:07 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-11 16:12 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-11 17:58 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-11 21:14 +0100
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-11 20:01 -0700
Re: Beginner....Decimal/Octal converter help Richard Damon <Richard@Damon-Family.org> - 2022-09-11 23:32 -0400
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-12 13:52 +0000
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-14 03:24 -0700
Re: Beginner....Decimal/Octal converter help Richard Damon <Richard@Damon-Family.org> - 2022-09-14 08:10 -0400
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-12-26 06:09 -0800
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-12 16:53 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-12 16:48 +0100
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-12 17:46 +0100
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-12 20:37 +0100
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-13 00:03 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-13 12:31 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-13 12:48 +0100
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-13 14:18 +0100
Re: Beginner....Decimal/Octal converter help Anton Shepelev <anton.txt@g{oogle}mail.com> - 2022-09-13 17:13 +0300
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-13 16:50 +0100
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-13 18:47 +0100
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-14 03:16 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-13 20:15 +0200
Re: Beginner....Decimal/Octal converter help Kaz Kylheku <480-992-1380@kylheku.com> - 2022-09-13 20:29 +0000
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-13 22:22 +0100
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-13 14:37 -0700
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-13 23:16 +0100
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-13 22:16 +0000
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-13 16:15 -0700
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-13 16:15 -0700
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-14 10:58 +0100
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-14 15:36 +0100
Re: Beginner....Decimal/Octal converter help Richard Harnden <richard.nospam@gmail.com> - 2022-09-14 21:53 +0100
Re: Beginner....Decimal/Octal converter help Kaz Kylheku <480-992-1380@kylheku.com> - 2022-09-14 05:55 +0000
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-14 10:10 +0200
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-14 07:54 -0700
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-14 18:32 +0200
Re: Beginner....Decimal/Octal converter help Bart <bc@freeuk.com> - 2022-09-14 18:39 +0100
Re: Beginner....Decimal/Octal converter help Kaz Kylheku <480-992-1380@kylheku.com> - 2022-09-15 01:12 +0000
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-15 09:11 +0200
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-15 08:07 -0700
Re: Beginner....Decimal/Octal converter help Kaz Kylheku <480-992-1380@kylheku.com> - 2022-09-14 18:40 +0000
Re: Beginner....Decimal/Octal converter help Kaz Kylheku <480-992-1380@kylheku.com> - 2022-09-14 05:45 +0000
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-14 12:11 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-14 09:57 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-14 03:09 +0100
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-14 10:29 +0200
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-14 15:14 +0100
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-14 07:36 -0700
Re: Beginner....Decimal/Octal converter help Öö Tiib <ootiib@hot.ee> - 2022-10-03 01:10 -0700
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-10-03 11:36 +0100
Re: Beginner....Decimal/Octal converter help Öö Tiib <ootiib@hot.ee> - 2022-10-04 02:13 -0700
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-10-04 16:27 +0100
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-13 11:48 -0700
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-14 10:38 +0200
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-14 14:27 +0000
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-14 07:58 -0700
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-16 13:06 -0700
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-16 13:16 -0700
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-12 17:55 +0000
Re: Beginner....Decimal/Octal converter help Kaz Kylheku <480-992-1380@kylheku.com> - 2022-09-12 18:22 +0000
Re: Beginner....Decimal/Octal converter help Ben Bacarisse <ben.usenet@bsb.me.uk> - 2022-09-12 20:41 +0100
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-11 15:45 -0700
Re: Beginner....Decimal/Octal converter help Keith Thompson <Keith.S.Thompson+u@gmail.com> - 2022-09-11 15:41 -0700
Re: Beginner....Decimal/Octal converter help David Brown <david.brown@hesbynett.no> - 2022-09-12 17:06 +0200
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-11 06:46 -0700
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-11 06:57 -0700
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-11 07:07 -0700
Neologism (Was: Beginner....Decimal/Octal converter help) gazelle@shell.xmission.com (Kenny McCormack) - 2022-09-11 14:18 +0000
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-11 16:33 +0000
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-13 15:40 -0700
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-09 23:08 +0000
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-11 06:37 -0700
Re: Beginner....Decimal/Octal converter help scott@slp53.sl.home (Scott Lurndal) - 2022-09-11 16:31 +0000
Re: Beginner....Decimal/Octal converter help Tim Rentsch <tr.17687@z991.linuxsc.com> - 2022-09-13 15:44 -0700
csiph-web