How to extract digits from a number from left to right?
Question:
I know that I can extract digits from a number from right to left by implementing something like:
while (number => 10)
digit = number modulo 10
number = number / 10
But is there a way to do it from left to right that works similar to this one, simply by using stuff like the modulo value?
Answers:
You can do like this,
number = 2164524
for i in str(number)[::-1]:
digit = int(i)
print digit
Convert number to string,reverse and iterate through it.
Mathematical way:
number = 2164524
while(number >= 10):
digit = number % 10
number = number / 10
print digit
print number # Last element will be in number
Alternative method with divmod
while n:
n, remainder = divmod(n, 10)
print remainder
Results:
4
2
5
4
6
1
If you don’t have problem with recursion approach then here is a solution with little change in your code:-
def get_digit(num):
if num < 10:
print(num)
else:
get_digit(num // 10)
print(num % 10)
Usage
>>> get_digit(543267)
5
4
3
2
6
7
You can do it “mathematical way”. If you take log10 from absolute value of number and round result up, then you get number of digits in a number (except for cases of 0 and 1). You can round up or round down, it will just alter origin of exponent.
Note that it uses log10 and other math functions, so it might be slower than using strings. And actual timeit shows just that:
>>> print(timeit.timeit('list(digits_left_to_right_str(12345))', setup='from __main__ import digits_left_to_right_str', number=10000))
>>> print(timeit.timeit('list(digits_left_to_right(12345))', setup='from __main__ import digits_left_to_right', number=10000))
0.02799521596170962
0.05542760493699461
def digits_left_to_right(number):
abs_value = abs(number)
if abs_value <= 1:
e = 1
else:
l10 = math.log10(abs_value)
e = math.ceil(l10)
while e > 0:
e -= 1
digit, abs_value = divmod(abs_value, 10 ** e)
yield digit
def digits_left_to_right_str(number):
for i in str(number)[::-1]:
digit = int(i)
yield digit
>>> import math
>>> def digitsLTR(num):
assert num > 0
start = int(math.log(num, 10))
for i in range(start, -1, -1):
power = 10 ** i
dig = num / power
yield dig
num -= dig * power
>>> list(digitsLTR(3567))
[3, 5, 6, 7]
Recursion is your friend:
def digits(n):
if n < 10:
print n
else:
q = n // 10
r = n - 10 * q
digits(q)
print r
The digits are extracted right-to-left as the recursion winds down, then printed left-to-right as the recursion unwinds. Recursion stops when n is only a single digit.
If you strictly wants the modulo – you will have to go into two phases:
- Find the closest power of 10.
- Use division and remainder.
Coming into code would be:
# 1
n, p = number, 1
while n >= 10:
n, p = n // 10, p * 10
# 2
while number >= 0:
number, digit, p = number % p, number // p, p // 10
Here is a generator which returns the digits of a positive integer in a left to right manner:
from math import floor, log10
def digits(n):
"""generator which returns digits in left to right order"""
k = floor(log10(n))
for e in range(k,-1,-1):
d,n = divmod(n,10**e)
yield d
For example,
>>> list(digits(2016))
[2, 0, 1, 6]
Here is mathematical way of doing this:
from math import log
number = 2164524
lenght = int(log(number, 10))
for i in range(lenght, -1, -1):
print( (number//(10**i)) % 10 )
You can do something like this.
number = 122322
num_str = str(number)
for num in num_str:
print num
Let’s n
be the number whose digits we want to compute from left to right.
Imagine first that we are given s
such that n < 10^s
(this isn’t usually the case, but for now let’s assume we know such an s
)
This means that
n = q 10^(s-1) + r
where q
is the quotient and r < 10^(s-1)
is the remainder of the division of n
by 10^(s-1)
.
Since n < 10^s
, we deduce that q <= 9
. If q > 0
, then q
must be the leftmost digit of n
. In other words
n = (q....)
where the dots represent the digits to the right.
Now, let’s use this understanding to write an algorithm that computes the digits of n
from left to right. We will assume that n > 0
.
[Find Max Power]
- Put
s := 0
and p := 1
(p
represents the power 10^s
)
- If
n < p
, go to 5 below.
- Put
s := s + 1
and p := p * 10
.
- Go to 2
[Find digits]
- Let
m := n
and a[s]
be the array of digits to compute
- Put
i := 1
(indexes are 1-based)
- Put
p := p / 10
(integer division)
- Let
q
and r
be the quotient and remainder of the division of m
by p
- Put
a[i] := q
and m := r
- If
i < s
put i := i + 1
and go to 7
At this point the array a[]
contains the digits from left to right of n
.
Note: By replacing everywhere 10
by any positive integer b
, you get the digits of n
in base b
.
Based on the answer of the dear user @AlokThakur, but improved and extended.
def get_digits_from_left_to_right(number, lst=None):
"""Return digits of an integer excluding the sign."""
if lst is None:
lst = list()
number = abs(number)
if number < 10:
lst.append(number)
return tuple(lst)
get_digits_from_left_to_right(number // 10, lst)
lst.append(number % 10)
return tuple(lst)
Examples of using with the CPython 3.5
In [99]: get_digits_from_left_to_right(-64517643246567536423)
Out[99]: (6, 4, 5, 1, 7, 6, 4, 3, 2, 4, 6, 5, 6, 7, 5, 3, 6, 4, 2, 3)
In [100]: get_digits_from_left_to_right(-9999999999999)
Out[100]: (9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9)
In [101]: get_digits_from_left_to_right(-100000000000)
Out[101]: (1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)
In [102]: get_digits_from_left_to_right(-9)
Out[102]: (9,)
In [103]: get_digits_from_left_to_right(0)
Out[103]: (0,)
In [104]: get_digits_from_left_to_right(9)
Out[104]: (9,)
In [105]: get_digits_from_left_to_right(100000000000000)
Out[105]: (1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)
In [106]: get_digits_from_left_to_right(9999999999999999)
Out[106]: (9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9)
In [107]: get_digits_from_left_to_right(123012312312321312312312)
Out[107]: (1, 2, 3, 0, 1, 2, 3, 1, 2, 3, 1, 2, 3, 2, 1, 3, 1, 2, 3, 1, 2, 3, 1, 2)
def digits(n):
if n == 0: # To use 0 instead of 10 allows the code to finish
# finish the extraction of digits
return n # Allows code re-utilization
else:
q = n // 10
r = n - 10 * q
digits(q)
print(r) # This is python 3
For example digits(546)
prints
5
4
6
C++ Solution. Storing the Digits in an Array.
int num = 120340;
int digits[10];
int size = 0;
while (num != 0)
{
int digit = num % 10;
digits[size++] = digit;
num = num / 10;
}
we have numbers array & size, traverse from last to first.
You can also resume the recursive implementation of @AlokThakur with a functional approach that appends results in a list:
def get_digits(num):
if num < 10:
return [num]
else:
return [*get_digits(num // 10), num % 10]
Why not just read it as characters of a string?
num = 123
total = 0
for d in str(num):
total += int(d)
print(total)
To complete AlokThakur answer, you can access the digits using a generator instead of just printing them.
def get_digit(num):
if num < 10:
yield num
else:
yield from get_digit(num // 10)
yield num % 10
>>> list(get_digit(543267))
[5, 4, 3, 2, 6, 7]
I know that I can extract digits from a number from right to left by implementing something like:
while (number => 10)
digit = number modulo 10
number = number / 10
But is there a way to do it from left to right that works similar to this one, simply by using stuff like the modulo value?
You can do like this,
number = 2164524
for i in str(number)[::-1]:
digit = int(i)
print digit
Convert number to string,reverse and iterate through it.
Mathematical way:
number = 2164524
while(number >= 10):
digit = number % 10
number = number / 10
print digit
print number # Last element will be in number
Alternative method with divmod
while n:
n, remainder = divmod(n, 10)
print remainder
Results:
4
2
5
4
6
1
If you don’t have problem with recursion approach then here is a solution with little change in your code:-
def get_digit(num):
if num < 10:
print(num)
else:
get_digit(num // 10)
print(num % 10)
Usage
>>> get_digit(543267)
5
4
3
2
6
7
You can do it “mathematical way”. If you take log10 from absolute value of number and round result up, then you get number of digits in a number (except for cases of 0 and 1). You can round up or round down, it will just alter origin of exponent.
Note that it uses log10 and other math functions, so it might be slower than using strings. And actual timeit shows just that:
>>> print(timeit.timeit('list(digits_left_to_right_str(12345))', setup='from __main__ import digits_left_to_right_str', number=10000))
>>> print(timeit.timeit('list(digits_left_to_right(12345))', setup='from __main__ import digits_left_to_right', number=10000))
0.02799521596170962
0.05542760493699461
def digits_left_to_right(number):
abs_value = abs(number)
if abs_value <= 1:
e = 1
else:
l10 = math.log10(abs_value)
e = math.ceil(l10)
while e > 0:
e -= 1
digit, abs_value = divmod(abs_value, 10 ** e)
yield digit
def digits_left_to_right_str(number):
for i in str(number)[::-1]:
digit = int(i)
yield digit
>>> import math
>>> def digitsLTR(num):
assert num > 0
start = int(math.log(num, 10))
for i in range(start, -1, -1):
power = 10 ** i
dig = num / power
yield dig
num -= dig * power
>>> list(digitsLTR(3567))
[3, 5, 6, 7]
Recursion is your friend:
def digits(n):
if n < 10:
print n
else:
q = n // 10
r = n - 10 * q
digits(q)
print r
The digits are extracted right-to-left as the recursion winds down, then printed left-to-right as the recursion unwinds. Recursion stops when n is only a single digit.
If you strictly wants the modulo – you will have to go into two phases:
- Find the closest power of 10.
- Use division and remainder.
Coming into code would be:
# 1
n, p = number, 1
while n >= 10:
n, p = n // 10, p * 10
# 2
while number >= 0:
number, digit, p = number % p, number // p, p // 10
Here is a generator which returns the digits of a positive integer in a left to right manner:
from math import floor, log10
def digits(n):
"""generator which returns digits in left to right order"""
k = floor(log10(n))
for e in range(k,-1,-1):
d,n = divmod(n,10**e)
yield d
For example,
>>> list(digits(2016))
[2, 0, 1, 6]
Here is mathematical way of doing this:
from math import log
number = 2164524
lenght = int(log(number, 10))
for i in range(lenght, -1, -1):
print( (number//(10**i)) % 10 )
You can do something like this.
number = 122322
num_str = str(number)
for num in num_str:
print num
Let’s n
be the number whose digits we want to compute from left to right.
Imagine first that we are given s
such that n < 10^s
(this isn’t usually the case, but for now let’s assume we know such an s
)
This means that
n = q 10^(s-1) + r
where q
is the quotient and r < 10^(s-1)
is the remainder of the division of n
by 10^(s-1)
.
Since n < 10^s
, we deduce that q <= 9
. If q > 0
, then q
must be the leftmost digit of n
. In other words
n = (q....)
where the dots represent the digits to the right.
Now, let’s use this understanding to write an algorithm that computes the digits of n
from left to right. We will assume that n > 0
.
[Find Max Power]
- Put
s := 0
andp := 1
(p
represents the power10^s
) - If
n < p
, go to 5 below. - Put
s := s + 1
andp := p * 10
. - Go to 2
[Find digits]
- Let
m := n
anda[s]
be the array of digits to compute - Put
i := 1
(indexes are 1-based) - Put
p := p / 10
(integer division) - Let
q
andr
be the quotient and remainder of the division ofm
byp
- Put
a[i] := q
andm := r
- If
i < s
puti := i + 1
and go to 7
At this point the array a[]
contains the digits from left to right of n
.
Note: By replacing everywhere 10
by any positive integer b
, you get the digits of n
in base b
.
Based on the answer of the dear user @AlokThakur, but improved and extended.
def get_digits_from_left_to_right(number, lst=None):
"""Return digits of an integer excluding the sign."""
if lst is None:
lst = list()
number = abs(number)
if number < 10:
lst.append(number)
return tuple(lst)
get_digits_from_left_to_right(number // 10, lst)
lst.append(number % 10)
return tuple(lst)
Examples of using with the CPython 3.5
In [99]: get_digits_from_left_to_right(-64517643246567536423)
Out[99]: (6, 4, 5, 1, 7, 6, 4, 3, 2, 4, 6, 5, 6, 7, 5, 3, 6, 4, 2, 3)
In [100]: get_digits_from_left_to_right(-9999999999999)
Out[100]: (9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9)
In [101]: get_digits_from_left_to_right(-100000000000)
Out[101]: (1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)
In [102]: get_digits_from_left_to_right(-9)
Out[102]: (9,)
In [103]: get_digits_from_left_to_right(0)
Out[103]: (0,)
In [104]: get_digits_from_left_to_right(9)
Out[104]: (9,)
In [105]: get_digits_from_left_to_right(100000000000000)
Out[105]: (1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)
In [106]: get_digits_from_left_to_right(9999999999999999)
Out[106]: (9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9)
In [107]: get_digits_from_left_to_right(123012312312321312312312)
Out[107]: (1, 2, 3, 0, 1, 2, 3, 1, 2, 3, 1, 2, 3, 2, 1, 3, 1, 2, 3, 1, 2, 3, 1, 2)
def digits(n):
if n == 0: # To use 0 instead of 10 allows the code to finish
# finish the extraction of digits
return n # Allows code re-utilization
else:
q = n // 10
r = n - 10 * q
digits(q)
print(r) # This is python 3
For example digits(546)
prints
5
4
6
C++ Solution. Storing the Digits in an Array.
int num = 120340;
int digits[10];
int size = 0;
while (num != 0)
{
int digit = num % 10;
digits[size++] = digit;
num = num / 10;
}
we have numbers array & size, traverse from last to first.
You can also resume the recursive implementation of @AlokThakur with a functional approach that appends results in a list:
def get_digits(num):
if num < 10:
return [num]
else:
return [*get_digits(num // 10), num % 10]
Why not just read it as characters of a string?
num = 123
total = 0
for d in str(num):
total += int(d)
print(total)
To complete AlokThakur answer, you can access the digits using a generator instead of just printing them.
def get_digit(num):
if num < 10:
yield num
else:
yield from get_digit(num // 10)
yield num % 10
>>> list(get_digit(543267))
[5, 4, 3, 2, 6, 7]