Append to an empty list using while loop - python-3.x

I've tried running this python script but it returns an empty list, I don't see what I'm missing but it seems I'm failing to append anything to the list. (The goal is to return a list of n numbers of prime numbers starting from 2, there are restrictions such as using only the while loop.) Appreciate any insights!!
def primes_list(n):
primes = []
count = 0
while count < n:
num = 1
divisor = 2
while num % divisor != 0 and num > divisor:
divisor += 1
if divisor == num:
primes.append(num)
count += 1
return primes

count is not used in the algorithm. Do you mean to use count everywhere num currently appears? Since you reset num to 1 on every iteration, every time around, the two boolean conditions are both false and the outer while effectively just counts up to n.

You don't need count as a counter. You just need to move num outside the while loop and increase num till n.
def primes_list(n):
primes = []
num = 1
while num < n:
divisor = 2
while num % divisor != 0 and num > divisor:
divisor += 1
if divisor == num:
primes.append(num)
num += 1
return primes

def primes_list(n):
num = 1
while num <= n:
div = 2
while num % div and num > div: div += 1
if div == num: yield num
num += 1
print(list(primes_list(100)))
This will simplify the code and alternative using yield generator.
Output:
[2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97]

Related

series of numbers separated by odd and even numbers using python [duplicate]

This question already has an answer here:
Code to produce a sequence with repeating pattern
(1 answer)
Closed 10 months ago.
a series of numbers each number is separated by odd and even numbers for example: separated by odd numbers(1,3,7,9...) - 1 2 5 10 17 26 37..... and separated by even numbers(2,4,6,8...) - 1 3 7 13 21 31 43.....
i want a python program for these series of numbers, thank you.
You could utilize a couple of generators:
def separated_by_odd_sequence() -> int:
num = 1
odd_increment = 1
while True:
yield num
num += odd_increment
odd_increment += 2
def separated_by_even_sequence() -> int:
num = 1
even_increment = 0
while True:
num += even_increment
even_increment += 2
yield num
def main() -> None:
separated_by_odd_sequence_gen = separated_by_odd_sequence()
first_10_separated_by_odd = [
next(separated_by_odd_sequence_gen) for _ in range(10)
]
print(f'{first_10_separated_by_odd = }')
separated_by_even_sequence_gen = separated_by_even_sequence()
first_10_separated_by_even = [
next(separated_by_even_sequence_gen) for _ in range(10)
]
print(f'{first_10_separated_by_even = }')
if __name__ == '__main__':
main()
Output:
first_10_separated_by_odd = [1, 2, 5, 10, 17, 26, 37, 50, 65, 82]
first_10_separated_by_even = [1, 3, 7, 13, 21, 31, 43, 57, 73, 91]

tribonacci sequence python code skips for loop within while loop

I wanted to use a for loop within a while loop to add up the last 3 numbers of the list and generate a new number to append into the existing list. However, the code would not enter the for loop within the while loop and I have no clue why.
What the function is supposed to do:
Take in a list of numbers (as signature)
Total up the LAST 3 numbers in the list and produce the next number to be appended
Continue step 2 until length of list == n
#my code
def tribonacci(signature, n):
total = 0
for i in range(len(signature)):
num = signature[i]
total += num
signature.append(total)
while len(signature) < n:
for j in range(-1,-4):
num = signature[j]
total += num
signature.append(num)
return signature
#Some sample test code:
print(tribonacci([1, 1, 1], 10))
print("Correct output: " + "[1, 1, 1, 3, 5, 9, 17, 31, 57, 105]")
print(tribonacci([0, 0, 1], 10))
print("Correct output: " + "[0, 0, 1, 1, 2, 4, 7, 13, 24, 44]")
print(tribonacci([300, 200, 100], 0))
print("Correct output: " + "[]")
UPDATE!
As suggested, I resetted the total count in the while loop by creating a total_2 = 0. I've also added the -1 to the range and changed .append(num) in the while loop block to .append(total_2).
def tribonacci(signature, n):
total = 0
for i in range(len(signature)):
num = signature[i]
total += num
signature.append(total)
while len(signature) < n:
total_2 = 0
for j in range(-1,-4, -1):
num = signature[j]
total_2 += num
signature.append(total_2)
return signature
However, this code doesnt work the 3rd print test code where n = 0. One of the users shared a much shorter code which works for ALL of the test code.
Try range(-1,-4,-1). You need to tell python to go backwards.
Just for the reference, I've implemented your function with a few improvements:
def tribonacci(signature, n):
signature = signature[:n]
while len(signature) < n:
signature.append(sum(signature[-3:]))
return signature

Is there a pythonic way to count the pairs that total up to whole minutes

I'm trying to find pairs of songs with durations that add up to whole minutes. Example given song lengths [10, 50, 90, 30]. Calculate the total number of different pairs. I'm expecting a return of 2 since the first and second pair to 60 seconds and the third and fourth songs pair to 120. But I'm instead getting 1 pair.
def pair_with_target_sum(songs, k):
n = len(songs)
count = 0
for i in range(0, n):
for j in range(i + 1, n):
if songs[i] + songs[j] == k:
count += 1
return count
def main():
print(pair_with_target_sum([10, 50, 90, 30], 60))
print(pair_with_target_sum([30, 20, 150, 100, 40], 60))
main()
There is different, and much simpler algorithm:
Create array with 60 buckets.
For each value in list run counts[value % k] += 1
Sum min(counts[n], counts[(n + k) % k]) (the weird calculation instead of just using k - n is to handle special case 0)
I'd use the itertools.combinations in conjunction with the modulo operator:
from itertools import combinations
def f(songs):
count = 0
for pair in combinations(songs, 2):
if sum(pair) % 60 == 0:
count += 1
return count
You can make your code work correctly with only changing a line and deleting the k parameter from your function definiton like this:
def pair_with_target_sum(songs):
n = len(songs)
count = 0
for i in range(0, n):
for j in range(i + 1, n):
if (songs[i] + songs[j]) % 60 == 0:
count += 1
return count
def main():
print(pair_with_target_sum([10, 50, 90, 30]))
print(pair_with_target_sum([30, 20, 150, 100, 40]))
print(pair_with_target_sum([60, 60, 60]))
main()
This works correctly for me when I run the code with different inputs.

Select a number randomly with probability proportional to its magnitude from the given array of n elements

Ex 1: A = [0 5 27 6 13 28 100 45 10 79]
let f(x) denote the number of times x getting selected in 100 experiments.
f(100) > f(79) > f(45) > f(28) > f(27) > f(13) > f(10) > f(6) > f(5) > f(0)
My code:
def pick_a_number_from_list(A,l):
Sum = 0
#l = len(A)
for i in range(l):
Sum+=A[i]
A_dash = []
for i in range(l):
b=A[i]/Sum
A_dash.append(b)
#print(A_dash)
series = pd.Series(A_dash)
cumsum = series.cumsum(skipna=False)
#print(cumsum[9])
sample_value = uniform(0.0,1.0)
r = sample_value
print(r)
#for i in range(l):
if r<cumsum[1]:
return 1
elif r>cumsum[1] and r <cumsum[2]:
return 2
elif r<cumsum[3]:
return 3
elif r<cumsum[4]:
return 4
elif r<cumsum[5]:
return 5
elif r<cumsum[6]:
return 6
elif r<cumsum[7]:
return 7
elif r<cumsum[8]:
return 8
elif r<cumsum[9]:
return 9
def sampling_based_on_magnitued():
A = [0,5,27,6,13,28,100,45,10,79]
n = len(A)
#for i in range(1,10):
num = pick_a_number_from_list(A,n)
print(A[num])
sampling_based_on_magnitued()
In mu code i am using multiple if else statement and because it is hardcoded
i can make by o/p right till 10 element in the list.
I want to make my code dynamic for any value in the list.
Here in my code i have restricted it to n=10
Pls tell me how can i right generic code which can replace all if - elseif statement with for loop
sum1=0;
for i in A:
sum1+=i;
x=0
list1=[]
for i in A:
list1.append(x+i/sum1)
x=x+i/sum1;
#list1 contsins cumulative sum
bit=uniform(0,1)
for i in range (0,len(list1)):
if bit<list1[i]:
return A[i]
you may use this
you can use random.choices
A = [0,5, 27, 6, 13, 28, 100, 45, 10, 79]
let no of random values want to pick it be 100 s0 k=100
w = [0.0, 0.01597444089456869, 0.08626198083067092, 0.019169329073482427, 0.04153354632587859, 0.08945686900958466, 0.3194888178913738, 0.14376996805111822, 0.03194888178913738, 0.2523961661341853]
weights is calculsted by using A[i]/(total sum of all the values of A)
x = random.choices(A,w,k=100)
print(x)
it displays the values from list A according to there weights
Some changes in Bitan Guha Roy's code to return just one value
import numpy as np
sum1=0;
for i in A:
sum1+=i;
x=0
list1=[]
for i in A:
list1.append(x+i/sum1)
x=x+i/sum1;
# list1 contains cumulative sum
bit=np.random.uniform(0.0,1.0,1)
for i in range (0,len(list1)):
if bit>=list1[i] and bit<list1[i+1]:
print(A[i+1]) # or return if under a function
import random
lst=[0, 5 ,27, 6, 13, 28, 100, 45, 10,79]
def pick_a_number_from_list(A):
weights1=[]
for i in A:
weights1.append(i/sum(lst))
selected_random_number = random.choices(A,weights=weights1,k=1)
return selected_random_number
def sampling_based_on_magnitued():
for i in range(1,100):
number=pick_a_number_from_list(lst)
print(number)
sampling_based_on_magnitued()
# used random.choices which gives option to choose random number according respective weights. Please suggest any modification if you've any

Time limit exceeded python

Im a newbie at python and i have a task. Given a number as input, i have to print the prime that belongs in the number/position on a list of primes starting from position 1 and not 0, until the input is 'END'. For example, if the input is 1, output should be the first prime which is 2, if the input is 5, output should be the 5th prime which is 11 and so. It works fine but after 3/4-digit numbers the output has a delay until i get the Error: Time limit exceeded. How can i make it run faster? Here's the code:
def primes_function(n):
primes = []
num = 2
while len(primes) <= n:
x = num // 2
while x > 1:
if num % x == 0:
break
x -= 1
else:
primes.append(num)
num += 1
return primes[n - 1]
#main
while True:
n = input()
if n == 'END':
break
elif n > '0':
n = int(n)
value = primes_function(n)
print(value)
Sorry if i made any mistakes in the description
enter image description here
I combined this answer (1) and this answer (2) to speed up the function. The two key ideas are: When testing primality of a candidate ...
... do not divide by every number (2, 3, 4, 5, 6, ...) but only by the preceding prime numbers (2, 3, 5, ...). Every non-prime number > 2 is has to have some prime factor.
... divide only by numbers that are ≤ sqrt(candidate).
import math
def nth_prime(n):
prime_list = [2]
candidate = 3
while len(prime_list) < n:
max_factor = math.sqrt(candidate)
is_prime = True
for p in prime_list:
if p > max_factor:
break
elif candidate % p == 0:
is_prime = False
break
if is_prime:
prime_list.append(candidate)
candidate += 2
return prime_list[-1]
Benchmark of different solutions:
n=9000 n=15000 n=25000 n=75000
your solution 1m38.455s - - -
linked answer (1) 0m 2.954s 8.291s 22.482s -
linked answer (2) 0m 0.352s 0.776s 1.685s 9.567s
this answer 0m 0.120s 0.228s 0.410s 1.857s
Brij's answer 0m 0.315s 0.340s 0.317s 0.318s
For every n the programs where started from scratch.
As we can see, Brij's Sieve Of Eratosthenes takes a fairly low constant amount of time. If you want to find big prime numbers below a fixed limit then that's the best solution (here n < 78499, as the 78499-th prime number is 1 000 003 which is bigger than the sieve list).
If you also want to find a lot of smaller or medium sized prime numbers or cannot accept a fixed limit then go with this solution.
def SieveOfEratosthenes():
n = 1000000
prime = [True for i in range(n+1)]
p = 2
count = 0
while (p * p <= n):
if (prime[p] == True):
count = count + 1
for i in range(p * p, n+1, p):
prime[i] = False
p += 1
seive = []
for p in range(2, n):
if prime[p]:
seive.append(p)
return seive
def primes_function(n , seive):
return seive[n - 1]
#main
seive = SieveOfEratosthenes()
while True:
n = input()
if n == 'END':
break
elif n > '0':
n = int(n)
value = primes_function(n,seive)
print(value)
Full working : https://ide.geeksforgeeks.org/QTSGQfhFV3
I have precomputed the primes below 10^6 and made a list of primes and accessed the nth prime number by the index.

Resources