I am using the following program to find the maximum sum and indices of the sum.I am able to get the right index but having trouble finding the right index.
def max_sum_new(a):
max_current = max_global = a[0]
r_index = 0
for i in range(1, len(a)):
max_current = max(a[i], max_current+a[i])
if max_current > max_global:
max_global = max_current
r_index = i
return (max_global, r_index)
#Driver Code:
my_arr = [-2, 3, 2, -1]
print(max_sum_new(my_arr))
I am getting
(5, 2)
which is expected but i also want to get the starting index which in this case should be 1
so i expect
(5, 1, 2)
is there any way to get a start index here? How should i put the variable to record start index?
You just need to apply the same logic as you did with r_index. Whenever you change the max_current, that's when the start of the maximum sub-array changes. In the end it looks like this
max_current = max_global = a[0]
r_index = 0
left_index = 0
for i in range(1, len(a)):
if a[i] > max_current + a[i]:
# Here is where your start index changes
left_index = i
max_current = a[i]
else:
max_current = a[i] + max_current
if max_current > max_global:
max_global = max_current
r_index = i
print(max_global, left_index, r_index)
Related
I am pretty new to coding and am currently struggling on how to optimize this code for larger lists.
import pandas as pd
import random
from time import time
rows = []
list1 = [random.randint(1, 100) for i in range(1_000_000)]
list2 = [random.randint(1, 100) for i in range(1_000_000)]
list3 = [random.randint(1, 100) for i in range(1_000_000)]
list4 = [random.randint(1, 100) for i in range(1_000_000)]
start = time()
for i in range(len(list1) - 1):
if list1[i] < list2[i] and list1[i + 1] > list2[i + 1]:
dict1 = {1: list1[i], 2: '+'}
rows.append(dict1)
elif list1[i] > list2[i] and list1[i + 1] < list2[i + 1]:
dict1 = {1: list1[i], 2: '-'}
rows.append(dict1)
if list3[i] < list4[i] and list3[i + 1] > list4[i + 1]:
dict1 = {1: list3[i], 2: '+'}
rows.append(dict1)
elif list3[i] > list4[i] and list3[i + 1] < list4[i + 1]:
dict1 = {1: list3[i], 2: '-'}
rows.append(dict1)
else:
dict1 = {1: list3[i], 2: '#'}
rows.append(dict1)
end = time()
print(end - start)
df = pd.DataFrame(rows)
with 10_000_000 entries it takes about 30 sec. It grows linear.
Is there a way to optimize it for larger numbers?
I feel like the for-loop and the if-else statements are the biggest time consumers, but I can't figure out a way to optimize them.
Thanks to #Tim Roberts and this question I figured out a way to optimize my code.
from time import time
list1 = np.array([random.randint(1, 100) for i in range(10_000_000)])
list2 = np.array([random.randint(1, 100) for i in range(10_000_000)])
list3 = np.array([random.randint(1, 100) for i in range(10_000_000)])
list4 = np.array([random.randint(1, 100) for i in range(10_000_000)])
start = time()
list_sub1 = np.subtract(list2, list1)
list_sub2 = np.subtract(list4, list3)
positive = list_sub1 > 0
positive2 = list_sub2 > 0
results = np.bitwise_xor(positive[1:], positive[:-1]).nonzero()[0]
results2 = np.bitwise_xor(positive2[1:], positive2[:-1]).nonzero()[0]
end = time()
print(end-start)
This way it only takes .25sec to analyze 10_000_000 entries instead of 30sec.
I changed the np.where(np.diff(np.sign(x)))suggested by #Tim Roberts to np.bitwise_xor(positive[1:], positive[:-1]).nonzero()[0]
because this gave me a time increase x2.
NOTE: This program does treat 0 as negative and only registers a change with >0 (1/-1). With np.sign() 0 is treated correctly(1/0/-1). In my case I don't need any further distinction so I chose the quicker method.
The Numpy Doc is great if you're new to vectorizing and numpy overall.
First I would like to thank you in advance.
I tried to write a quick sort in python3, but it recurs infinitely.
Here's my code:
def partition(lst, l, h):
lst.append(float("inf"))
pivot = lst[0]
i, j = l+1, h
while i < j:
while lst[i] < pivot:
i += 1
while lst[j] > pivot:
j -= 1
if i < j:
lst[i] , lst[j] = lst[j], lst[i]
else:
lst = lst[1:i] + [pivot] + lst[i:]
return lst[:-1], i
def quickSort(lst, l, h):
if l < h-1:
mid = (l + h)//2
lst[l:h], mid = partition(lst[l:h], 0, h-l)
quickSort(lst, l, mid)
quickSort(lst, mid, h)
lst1 = [10, 12, 8, 16, 2, 6, 3, 9, 5]
quickSort(lst1, 0, 9)
In recursive algorithms, you should be careful about the initial step of the algorithm. For example, in your case, you need to sort the given array manually without any recursion with the size of 2.
I need to create a matrix, where the user can input his values and determine the maximum value of the matrix, the minimum value and the average value of all matrix's data
I created the matrix, where I can input my own values and I tried to write which could determine the maximum and minimum value. However, after several checks, I understood, that my piece of code, which determines max and min values, doesn't work.
line = int(input('Enter the amount of lines:'))
columns = int(input('Enter the amount of columns:'))
matrix = []
for i in range(0, columns):
matrix.append([])
for i in range(0, line):
for j in range(0, columns):
matrix[i].append(j)
matrix[i][j] = 0
for i in range(0, line):
for j in range(0,columns):
matrix[i][j] = int(input('Enter the value:'))
avg = matrix
for i in range(0, line):
for j in range(0, columns):
max_val = matrix[j]
min_val = matrix[j]
for j in range(0, len(matrix[j]), 1):
max_val = max(max_val, matrix[j])
min_val = min(min_val, matrix[j])
maxVal = max_val[0]
minVal = min_val[0]
for i in range(0, len(max_val), 1):
maxVal = max(maxVal, max_val[i])
minVal = min(minVal, min_val[i])
print(matrix)
print('The maximum value is ' + str(maxVal))
print('The minimum value is ' + str(minVal))
I excepted the result, which will print me the matrix, maximum value, minimum value and average value
One way of doing it with Python lists is this:
(I'll just do find_min(), as find_max() and compute_mean() would be pretty much the same.)
import random
def gen_random_matrix(rows, cols, min_val=1, max_val=100):
return [
[random.randint(min_val, max_val) for j in range(cols)]
for i in range(rows)]
def find_min(matrix):
rows = len(matrix)
cols = len(matrix[0])
min_i, min_j = 0, 0
min_val = matrix[min_i][min_j]
for i in range(rows):
for j in range(cols):
if matrix[i][j] < min_val:
min_i = i
min_j = j
min_val = matrix[i][j]
return min_val, min_i, min_j
random.seed(0)
matrix = gen_random_matrix(3, 4)
print(matrix)
# [[50, 98, 54, 6], [34, 66, 63, 52], [39, 62, 46, 75]]
print(find_min(matrix))
# (6, 0, 3)
I am trying to define a function, median, that consumes a list of numbers and returns the median number from the list. If the list is empty, then I want to return None. To calculate the median, I need to find the middle index of the list after it has been sorted. Do not use a built-in function.
SURVEY_RESULTS = [1.5, 1, 2, 1.5, 2, 3, 1, 1, 1, 2]
def median(SURVEY_RESULTS):
length = 0
order = sorted(SURVEY_RESULTS)
I'm not sure how to use indexing to now determine the median.
Here is my implementation:
def QuickSort(myList,start,end):
if start < end:
i,j = start,end
base = myList[i]
while i < j:
while (i < j) and (myList[j] >= base):
j = j - 1
myList[i] = myList[j]
while (i < j) and (myList[i] <= base):
i = i + 1
myList[j] = myList[i]
myList[i] = base
QuickSort(myList, start, i - 1)
QuickSort(myList, j + 1, end)
return myList
def median(l):
half = len(l) // 2
return (l[half] + l[~half])/2 # Use reverse index
SURVEY_RESULTS = [1.5, 1, 2, 1.5, 2, 3, 1, 1, 1, 2]
# Sort first
QuickSort(SURVEY_RESULTS, 0, len(SURVEY_RESULTS)-1)
result = median(SURVEY_RESULTS)
print (result)
My denomination "5" is not showing up and how do you reverse the dict easily. i dont want extra 5 line of code.lol
Can you guys help me out with it?
the code is working so far.
here is my code with a test case
def change(target, coins):
result = dict()
i= len(coins) -1
while i> 0:
coin = coins[i]
numOfThisCoin= target // coin
result[coin] = numOfThisCoin
target -= coin * numOfThisCoin
i-= 1
return result
print(change(185, (5, 10, 25, 100, 200)))
i am getting output
{200: 0, 100: 1, 25: 3, 10: 1}
but want it like
{5: 0, 10: 1, 25: 3, 100: 1, 200: 0}
Here is the corrected code for your problem:
from collections import OrderedDict
def change(target, coins):
result = dict()
i= len(coins) -1
while i>= 0:
coin = coins[i]
numOfThisCoin= target // coin
result[coin] = numOfThisCoin
target -= coin * numOfThisCoin
i-= 1
res = OrderedDict(sorted(result.items()))
return res
print(change(185, (5, 10, 25, 100, 200)))
If you (not only 25 you can access any coin denomination)
print(res[25])
Output will be
3
in this case.
dict- it does not keep the elements in order. You have to use OrderedDict for sorting the elements in the order you want. For more info follow the below link:
http://docs.python.org/library/collections.html#collections.OrderedDict
def change(target, coins):
result = dict()
i= len(coins) -1
while i>= 0:
coin = coins[i]
numOfThisCoin= target // coin
result[coin] = numOfThisCoin
target -= coin * numOfThisCoin
i-= 1
return dict(sorted(result.items()))
print(change(185, (5, 10, 25, 100, 200)))