I am looking to write a function in python that places a decimal point into some string.
for example if the string I give is '12355' and then I put the point place in 2
the output should skip the first two numbers and show '12.355'
please help,
thank you
Here
place = 3
number = "12345"
result = number[:place] + "." + number[place:]
print(result)
The result will have the decimal point 3 characters from the first one.
When I run it the output is
123.45
If you were to do a function, then
def insert_decimal(position,number):
return number[:position] + "." + number[position:]
You can use string indexing, as if it were a list:
def insert_decimal_point(number, position):
return number[:position] + "." + number[position:]
def add_decimal_point(s, n):
return f'{s[:n]}.{s[n:]}' if 0 < n < len(s) else s
add_decimal_point("23567", 2)
23.567
If n is greater or equal to the length of the string or if it is negative, the original string is returned:
add_decimal_point("23567", 10)
23567
Or you can treat this string mathematically as a number:
s = "12355"
n = float(s)
length = len(s)
place = 2
power = length - place
print(n / (10 ** power))
lets separate logic into the function:
def decimal_point(s, place):
n = float(s)
length = len(s)
power = length - place
return n / (10 ** power)
I want to use a recursive algorithm for the function, which should print out the sum of all the digits of a given number.
Here is my code. For example, sum_of_digits(343) will return an output of 10.
numbers = [1, 2]
def sum_of_digits(n):
for n in
sum_of_digits(343)
The output I'm trying to achieve: 10
If you have to use recursion, one method would be to get the individual digits by modding n with 10 and adding that to the sum of the remaining digits (computed by sum_of_digits(n // 10):
def sum_of_digits(n):
if n < 10:
return n
return (n % 10) + sum_of_digits(n // 10)
print(sum_of_digits(343))
Output:
10
def sum_of_digits(n):
result = 0
for x in str(n):
result += int(x)
return result
sum_of_digits(343) # 10
How about this simplest solution:
number = 343
sum_of_digits = sum(map(int, str(number)))
print(sum_of_digits)
10
my homework is "Write a function that takes in two numbers and recursively multiplies them together", the solution for integers appears in the website in few questions, but is is possible for floats i wrote a code that can handle one float but I can't imagine how to deal with 2 as a novice i wonder is there such possibility that's my code
def multy(n, m):
# deals with one float situation
if m % 1 != 0:
return multy(m, n)
else:
if m == 0:
return 0
elif m < 0:
return -(n - multy(n, m+1))
else:
return n + multy(n, m-1)
You can "convert" your float to int and use your multy function, then "convert" it back to the float:
def fmulty(n, m):
nd = len(str(n).split('.')[1])
md = len(str(m).split('.')[1])
return multy(n * pow(10, nd), m * pow(10, md)) / pow(10, md+nd)
The idea is to make n and m integers by shifting the decimal to the right. For instance you have n = 1.234, then you need to multiply by 1,000 (nd=3). The same for m in md. Once done, you can use multy and divide the result by 1E(nd+md). Let say m = 5.67 then you have md = 2. You then need to divide the result by 1E5, i.e. 100,000.
So I was studying recursion function online. And the one question asks me to write a function to add up a number's digits together. For example (1023) -> 1 + 0 + 2 + 3 = 6. I used % and // get get rid of a digit each time. However, I don't know how to add them up together. The closest I can get is to print out each digit. Can anyone help me solve it or give me a hint please?
def digitalSum(n):
if n < 10:
sum_total = n
print(sum_total)
else:
sum_total = n % 10
digitalSum((n - (n % 10))//10)
print(sum_total)
digitalSum(1213)
Your function should return the current digit plus the sum of the rest of the digits:
def digitalSum(n):
if n < 10: return n
return n % 10 + digitalSum(n // 10)
print digitalSum(1213)
For completeness, you can also handle negative numbers:
def digitalSum(n):
if n < 0: sign = -1
else: sign = 1
n = abs(n)
if n < 10: return n
return sign * (n % 10 + digitalSum(n // 10))
print digitalSum(1213)
A correct version of your function is as follows:
from math import log10
def sum_digits(n, i=None):
if i is None:
i = int(log10(abs(n)))
e = float(10**i)
a, b = (n / e), (abs(n) % e)
if i == 0:
return int(a)
else:
return int(a) + sum_digits(b, (i - 1))
print sum_digits(1234)
print sum_digits(-1234)
Example:
$ python -i foo.py
10
8
>>>
Updated: Updated to properly (IHMO) cope with negative numbers. e.g: -1234 == -1 + 2 + 3 + 4 == 8
NB: Whilst this answer has been accepted (Thank you) I really think that perreal's answer should have been accepted for simplicity and clarity.
Also note: that whilst my solution handles negative numbers and summing their respective digits, perreal clearly points out in our comments that there are ate least three different ways to interpret the summing of digits of a negative number.
I am trying to find an efficient way to compute Euler's totient function.
What is wrong with this code? It doesn't seem to be working.
def isPrime(a):
return not ( a < 2 or any(a % i == 0 for i in range(2, int(a ** 0.5) + 1)))
def phi(n):
y = 1
for i in range(2,n+1):
if isPrime(i) is True and n % i == 0 is True:
y = y * (1 - 1/i)
else:
continue
return int(y)
Here's a much faster, working way, based on this description on Wikipedia:
Thus if n is a positive integer, then φ(n) is the number of integers k in the range 1 ≤ k ≤ n for which gcd(n, k) = 1.
I'm not saying this is the fastest or cleanest, but it works.
from math import gcd
def phi(n):
amount = 0
for k in range(1, n + 1):
if gcd(n, k) == 1:
amount += 1
return amount
You have three different problems...
y needs to be equal to n as initial value, not 1
As some have mentioned in the comments, don't use integer division
n % i == 0 is True isn't doing what you think because of Python chaining the comparisons! Even if n % i equals 0 then 0 == 0 is True BUT 0 is True is False! Use parens or just get rid of comparing to True since that isn't necessary anyway.
Fixing those problems,
def phi(n):
y = n
for i in range(2,n+1):
if isPrime(i) and n % i == 0:
y *= 1 - 1.0/i
return int(y)
Calculating gcd for every pair in range is not efficient and does not scales. You don't need to iterate throught all the range, if n is not a prime you can check for prime factors up to its square root, refer to https://stackoverflow.com/a/5811176/3393095.
We must then update phi for every prime by phi = phi*(1 - 1/prime).
def totatives(n):
phi = int(n > 1 and n)
for p in range(2, int(n ** .5) + 1):
if not n % p:
phi -= phi // p
while not n % p:
n //= p
#if n is > 1 it means it is prime
if n > 1: phi -= phi // n
return phi
I'm working on a cryptographic library in python and this is what i'm using. gcd() is Euclid's method for calculating greatest common divisor, and phi() is the totient function.
def gcd(a, b):
while b:
a, b=b, a%b
return a
def phi(a):
b=a-1
c=0
while b:
if not gcd(a,b)-1:
c+=1
b-=1
return c
Most implementations mentioned by other users rely on calling a gcd() or isPrime() function. In the case you are going to use the phi() function many times, it pays of to calculated these values before hand. A way of doing this is by using a so called sieve algorithm.
https://stackoverflow.com/a/18997575/7217653 This answer on stackoverflow provides us with a fast way of finding all primes below a given number.
Oke, now we can replace isPrime() with a search in our array.
Now the actual phi function:
Wikipedia gives us a clear example: https://en.wikipedia.org/wiki/Euler%27s_totient_function#Example
phi(36) = phi(2^2 * 3^2) = 36 * (1- 1/2) * (1- 1/3) = 30 * 1/2 * 2/3 = 12
In words, this says that the distinct prime factors of 36 are 2 and 3; half of the thirty-six integers from 1 to 36 are divisible by 2, leaving eighteen; a third of those are divisible by 3, leaving twelve numbers that are coprime to 36. And indeed there are twelve positive integers that are coprime with 36 and lower than 36: 1, 5, 7, 11, 13, 17, 19, 23, 25, 29, 31, and 35.
TL;DR
With other words: We have to find all the prime factors of our number and then multiply these prime factors together using foreach prime_factor: n *= 1 - 1/prime_factor.
import math
MAX = 10**5
# CREDIT TO https://stackoverflow.com/a/18997575/7217653
def sieve_for_primes_to(n):
size = n//2
sieve = [1]*size
limit = int(n**0.5)
for i in range(1,limit):
if sieve[i]:
val = 2*i+1
tmp = ((size-1) - i)//val
sieve[i+val::val] = [0]*tmp
return [2] + [i*2+1 for i, v in enumerate(sieve) if v and i>0]
PRIMES = sieve_for_primes_to(MAX)
print("Primes generated")
def phi(n):
original_n = n
prime_factors = []
prime_index = 0
while n > 1: # As long as there are more factors to be found
p = PRIMES[prime_index]
if (n % p == 0): # is this prime a factor?
prime_factors.append(p)
while math.ceil(n / p) == math.floor(n / p): # as long as we can devide our current number by this factor and it gives back a integer remove it
n = n // p
prime_index += 1
for v in prime_factors: # Now we have the prime factors, we do the same calculation as wikipedia
original_n *= 1 - (1/v)
return int(original_n)
print(phi(36)) # = phi(2**2 * 3**2) = 36 * (1- 1/2) * (1- 1/3) = 36 * 1/2 * 2/3 = 12
It looks like you're trying to use Euler's product formula, but you're not calculating the number of primes which divide a. You're calculating the number of elements relatively prime to a.
In addition, since 1 and i are both integers, so is the division, in this case you always get 0.
With regards to efficiency, I haven't noticed anyone mention that gcd(k,n)=gcd(n-k,n). Using this fact can save roughly half the work needed for the methods involving the use of the gcd. Just start the count with 2 (because 1/n and (n-1)/k will always be irreducible) and add 2 each time the gcd is one.
Here is a shorter implementation of orlp's answer.
from math import gcd
def phi(n): return sum([gcd(n, k)==1 for k in range(1, n+1)])
As others have already mentioned it leaves room for performance optimization.
Actually to calculate phi(any number say n)
We use the Formula
where p are the prime factors of n.
So, you have few mistakes in your code:
1.y should be equal to n
2. For 1/i actually 1 and i both are integers so their evaluation will also be an integer,thus it will lead to wrong results.
Here is the code with required corrections.
def phi(n):
y = n
for i in range(2,n+1):
if isPrime(i) and n % i == 0 :
y -= y/i
else:
continue
return int(y)