So I am new to python and here is my python code:
def main():
N = 1
players = 10
for _ in range(N):
maxi = 0
t1 = [3, 6, 7, 5, 3, 5, 6, 2, 9, 1]
t2 = [2, 7, 0, 9, 3, 6, 0, 6, 2, 6]
for i in range(players):
count = t2[i]+1
flag = 0
def calcWin(count):
global maxi,flag
if(count in t1):
flag = 1
maxi = maxi + 1
t1.remove(count)
else:
count = count + 1
if(count<=max(t1)):
calcWin(count)
calcWin(count)
print(flag)
main()
I want the variable 'maxi' to be accessible inside the function calcWin(). So it declared the variable as global inside the function. But it throws 'NameError'. I want the variable 'maxi' to reinitialize to 0 for each 'N'. Another thing is that the 'flag' variable always prints 0 even though it satisfies the condition 'if(count in t1)'. (Note: I declared 'flag' as global inside the function). Can somebody help me with this?
As you are asking in the comment for a way to do this without global variables, the following could be a proposal. Please understand that I just imitated what I think you intended with your original code. You may have to adapt your algorithm...
def main():
n = 1
players = 10
for _ in range(n):
maxi_persistent = 0
t1 = [3, 6, 7, 5, 3, 5, 6, 2, 9, 1]
t2 = [2, 7, 0, 9, 3, 6, 0, 6, 2, 6]
for i in range(players):
def calc_win(count, maxi):
flag = False
if count in t1:
flag = True
maxi += 1
t1.remove(count)
else:
count += 1
if count <= max(t1):
return calc_win(count, maxi)
return maxi, flag
maxi_persistent, win_flag = calc_win(count=t2[i] + 1, maxi=maxi_persistent)
print(win_flag)
if __name__ == "__main__":
main()
Please note that flag, as you use it in your question, does not need any global handling. It is 0 at each call of the function, so I just set it to 0 (or False) in the beginning of the function instead.
Related
Here's the problem. The input is a list of integers. If more than three adjacent numbers appear next to each other they should be dropped and the operation goes again. Kind of similar to the Iphone game, where player needs to pop lines of three or more balls of the same colors. The output should be the count of the balls that will be removed.
The algorithm is as follows. Starting with a sample list of say [3,3,4,4,4,4,3,2].
First iteration should remove the 4,4,4,4 - so the list would become [3,3,3,2], and the intermediary output of removed numbers will be 4.
Second iteration should remove 3,3,3 - so the final list would be [2] and final count of removed numbers - 7.
The first implementation for three consecutive items came from another stackoverflow thread - Remove triplets of adjacent numbers from the list
Here's the working function implementation for exactly 3 consecutive numbers:
def balls(l):
values = l
while len(values) >= 3:
print(values) #for demonstrative purposes of this question
for x in range(0,len(values)-2):
if values[x] == values[x+1] and values[x] == values[x+2]:
values = values[:x] + values[x+3:]
break
else:
break
print(values) #for demonstrative purposes of this question
return len(l) - len(values)
balls([3, 3, 4, 4, 4, 3, 4])
Output:
[3, 3, 4, 4, 4, 3, 4]
[3, 3, 3, 4]
[4]
6
How could I update the implementation to include the more general solution of removing 3+ consecutive numbers. I am thinking about tracking the start and end index of the consecutive duplicates, then subsetting the list. However, not sure how to implement that. Here are the tests that should work.
if __name__ == "__main__":
test1 = [3, 3, 4, 4, 4, 3, 4]
print(balls(test1))
#Output should be 6
test2 = [5, 5, 5, 5, 5, 5, 5, 5]
print(balls(test2))
#Output should be 8
test3 = [5, 7, 8, 3]
print(balls(test3))
#Output should be 0
def remove_consecutive(l, length):
amount = len(l)
count = 1
start = 0
current = l[0]
i = 1
while i < len(l):
if l[i] == current:
count += 1
else:
if count >= length:
for i in range(count):
l.pop(start)
start = 0
i = 0
current = l[0]
else:
start = i
current = l[i]
count = 1
i+=1
if count >= length:
for i in range(count):
l.pop(start)
return amount - len(l)
Wuff, i got it. My brain is kinda stinky lately so it took so long.
Here is my code, it works well. But I think there may be better ways to achieve higher efficiency.
def remove_consecutive(lst):
len_init = len(lst)
contain_tuplets = True
while contain_tuplets:
for i in range(len(lst)-2):
indices_to_pop = []
if lst[i]==lst[i+1]==lst[i+2]:
indices_to_pop.extend([i, i+1, i+2])
for j in range(i+3,len(lst)):
if lst[j] == lst[i]:
indices_to_pop.append(j)
else:
break
[lst.pop(i) for _ in indices_to_pop]
contain_tuplets = True
break
else:
contain_tuplets = False
count_removed_numbers = len_init - len(lst)
return count_removed_numbers, lst
test case1:
lst = [3,3,4,4,4,4,3,2]
remove_consecutive(lst)
output
(7, [2])
test case 2:
lst = [2, 2, 1, 1, 1, 2, 1]
remove_consecutive(lst)
output:
(6, [1])
def remove_consecutive(l, length):
amount = 0
count = 1
current = l[0]
for i in range(1, len(l)):
if l[i] == current:
count += 1
if count > length:
amount += 1
elif count == length:
amount += length
else:
current = l[i]
count = 1
return amount
I want to let the user choose either to move elements in an rng list either to the left, right or let them choose. I saw a similar post, but after reading it I did not see a way to choose which direction and do multiple repeats of the process.
import random
randlist = []
for i in range(10):
randlist.append(random.randint(0,10))
x = input("Right? Left? Choose?")
if x == "Right":
#Move all elements to the right once
elif x == "Left":
#Move all elements to the left once
else:
#Let User input both direction and amount of moves to the specified side
Slicing the array helps here. Only when rotating more than the
length of array needs to be taken care. if lenght of array is
10 then rotaing 13 times is same as rotaing 3 times.
Code:
import random
def rotate_right(arr, n):
m = n % len(arr)
m = len(arr) - m
return arr[m:] + arr[0:m]
def rotate_left(arr, n):
n = n % len(arr)
return arr[n:] + arr[0:n]
randlist = []
for i in range(10):
randlist.append(random.randint(0, 10))
print(randlist)
print(rotate_right(randlist,13))
print(rotate_left(randlist,14))
x = input("Right? Left? Choose?")
if x == "Right":
print(rotate_right(randlist,1))
elif x == "Left":
print(rotate_left(randlist,1))
Output:
[0, 7, 3, 3, 0, 4, 0, 6, 6, 3]
[6, 6, 3, 0, 7, 3, 3, 0, 4, 0]
[0, 4, 0, 6, 6, 3, 0, 7, 3, 3]
Right? Left? Choose?
I wrote this code for a simple linear search:
def floor(array, target):
i = 0
while i < len(array):
if array[i] == target:
print("The target value can be found at index: " + str(array[i]))
break
else:
i = i + 1
floor([1, 2, 3, 4, 4, 5, 6, 7, 8, 9, 9, 10, 11, 12, 13, 14], 5)
The problem I'm having is that it's not returning the values I want. For some reason it doesn't start counting at 0, so when I make the target 1 it tells me the index is 1. Likewise, if I make the target 4 it will give me the second value of 4 at index 4 rather than the one at index 3. Even when the target is a higher number, it only seems to count the value of 4 once. I'm not sure what I'm doing wrong, can anyone offer some advice?
You're printing out the value at the index ie array[i] instead of i.
You're printing the value of the array at the index instead of the index itself. This fixes it. Also consider a return instead of a print statement.
def floor(array, target):
i = 0
while i < len(array):
if array[i] == target:
print("The target value can be found at index: " + str(i))
return i
else:
i = i + 1
four_ind = floor([1, 2, 3, 4, 4, 5, 6, 7, 8, 9], 4) # returns 3
try this:
def floor(array, target):
for i, value in enumerate(array):
if value == target:
print('target is in:', i)
floor([1,2,3,4,5, 4, 4,6], 4)
**I need to make a quicksort algorithm but so that it uses only one list and does swaps inside of it. I managed to make it "sort" or position the first element but now i don't know how to implement the recursion. The biggest problem I'm having is how to recursively work on a part of the list instead of making the new one. Here is my code:
-------------------------------------------------------------------------------**
New code, same problem.
Here is my code. It does the job but gets stuck in the loop.
def qsort(n,l,g):
if l is None:
l=0
if g is None:
g=len(n)
if g-l<=1:
return n
print g-l
p=n[l]
i=1+l
j=1+l
for x in n[l+1:g]:
if x<p:
n[i],n[j]=n[j],n[i]
i+=1
j+=1
n[l],n[i-1]=n[i-1],n[l]
ls=0
le=i-1
gs=i
ge=j
print n
qsort(n,ls,le)
qsort(n,gs,ge)
Can someone give me any suggestions, I'm lost. Can't find whats wrong or how to fix it.
Know its messy but cant do better atm :D
Write it like this:
def qsort(li, lo=None, hi=None):
if lo is None:
lo = 0
if hi is None:
hi = len(li) - 1
...
...
if hi - lo > 1:
qsort(## left half ##)
qsort(## right half ##)
lo and hi are the smallest and largest indexes you should look at in li, respectively.
Swap version of quicksort.
quicksort([10, 0, 9, 1, 8, 2, 7, 3, 6, 4, 5]) >> [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
quicksort([0, 4, 2, 3, 6]) >> [0, 2, 3, 4, 6]
def quicksort(seq):
if len(seq) <= 1:
return seq
pivot_index = len(seq)-1
i = 0
while i < pivot_index:
if seq[i] > seq[pivot_index] and pivot_index-1 == i:
seq[i], seq[pivot_index] = seq[pivot_index], seq[i]
pivot_index -= 1
i = 0
elif seq[i] > seq[pivot_index] and pivot_index > 1:
seq[pivot_index-1], seq[pivot_index] = seq[pivot_index], seq[pivot_index-1]
seq[i], seq[pivot_index] = seq[pivot_index], seq[i]
pivot_index -= 1
i = 0
else:
i += 1
return quicksort(seq[:pivot_index]) + [seq[pivot_index]] + quicksort(seq[pivot_index+1:])
I have this function here:
def swap_cards(deck, index_deck):
swap_deck = []
after_index = []
bandf_index = []
if index_deck >= len(deck):
for i in range(0, len(deck) + 1):
if deck[i] == index_deck:
after_index += [deck[0]]
else:
bandf_index += [deck[i]]
swap_deck += [deck[index_deck]] + bandf_index[1:index_deck - 1] + after_index
Every time I try to input an index that is greater than or equal to the deck length I get the error 'list index out of range'
Example:
swap_cards([0, 1, 2, 3, 4, 5, 6, 7, 8, 9], 9)
I expect [9, 1, 2, 3, 4, 5, 6, 7, 8, 0] but am instead getting 'list index out of range'.
Switching the last and the first number, I don't know what I am doing wrong.
You have a problem with len(). Assuming your index_deck is 9 as in the example above:
if index_deck >= len(deck):
for i in range(0, len(deck) + 1):
This range will yield [0,1,2,3,4,5,6,7,8,9,10,11]
if deck[i] == index_deck:
after_index += [deck[0]]
Since array indexes are zero-based, the above line will generate the error. deck[10] and deck[11] don't exist.
else:
bandf_index += [deck[i]]
Fixing the above len() statement will fix this as well (again, you may try to access deck[10] if the if statement is false.
swap_deck += [deck[index_deck]] + bandf_index[1:index_deck - 1] + after_index
Final thing: you verify that if index_deck >= len(deck):. This will break the above line at deck[index_check] since here you will always access an index which does not exist.