Bigrams frequency in str and dict comprehensions - python-3.x

I want to get dictionary with 'bigram: frequency' where bigram = str[i] + str[i + 1]. So this is my solution:
f_dict = {}
for i in range(0, len(string) - 1, step):
if string[i] + string[i + 1] in f_dict:
f_dict[string[i] + string[i + 1]] += 1
else:
f_dict[string[i] + string[i + 1]] = 1
Is it possible to write this with dict comprehensions in one line, or is there a better solution (within the meaning of performance)?

You can do as follows :
s = 'abaabaab' # Your string
# Dictionary comprehension
dic = {k : s.count(k) for k in {s[i]+s[i+1] for i in range(len(s)-1)}}
Result :
In[2]: dic
Out[3]: {'aa': 2, 'ab': 3, 'ba': 2}

Related

Multiplication of polynomials

I have polynomial coefficients. How to get a list of coefficients e.g. by multiplying 10 polynomials?
For example for two polynomials.
(x + 2)*(x + 2) = x^2 + 4x + 4
[1,2] * [1,2] = [1, 4, 4]
I am trying to solve a codewars task which gives me a list of roots and I have to return a polynomial.
My first idea was function from numpy, poly but there is too much difference with large numbers. Thank u!
Source: https://www.codewars.com/kata/5b2d5be2dddf0be5b00000c4
My code:
import re
from numpy import poly
from math import fabs
def polynomialize(roots):
result = ''
data = list(filter(lambda x : x[0] != 0, zip(poly(roots).tolist(), range(len(roots), -1, -1))))
for coe, power in data:
if coe > 0:
result += f'+ {int(coe)}x^{power} '
else:
result += f'- {int(fabs(coe))}x^{power} '
result = re.sub(r'(x\^1)(?![0-9]+)', 'x', result).replace('x^0', '')
result = re.sub(r'(?<![0-9])(1x)','x', result)
return result[2:] + '= 0'
This is likely related to the integer type that numpy uses in its arrays, while the inputs and the resulting coefficients may involve greater numbers than these integers can hold (wrapping around).
You could do this to get data:
coeff = [1]
for r in roots:
coeff = [t[1] - r * t[0] for t in zip(coeff + [0], [0] + coeff)]
data = list(filter(lambda x : x[1] != 0,
reversed(list(enumerate(coeff)))))
for power, coe in data: # notice the pairs are in reverse compared to your loop
Also fabs is limited to integer. I would change int(fabs(coe)) to -int(coe).
I submitted this solution and it was accepted:
import re
def polynomialize(roots):
coeff = [1]
for r in roots:
coeff = [t[1] - r * t[0] for t in zip(coeff + [0], [0] + coeff)]
data = list(filter(lambda x : x[1] != 0,
reversed(list(enumerate(coeff)))))
result = ''
for power, coe in data:
if coe > 0:
result += f'+ {int(coe)}x^{power} '
else:
result += f'- {-int(coe)}x^{power} '
result = re.sub(r'(x\^1)(?![0-9]+)', 'x', result).replace('x^0', '')
result = re.sub(r'(?<![0-9])(1x)','x', result)
return result[2:] + '= 0'
Is it what you want?
from sympy import symbols, Poly
x = symbols("x")
pol1 = Poly(x + 2)
pol = pol1 ** 2
pol.all_coeffs()
# [1, 4, 4]

(python) Why doesn't .append() work here?

I have some code that effectively replaces this excel spreadsheet where I am trying to find the difference between two times. Depending on the state of the second column of that value I want to segregate this into two columns.
I converted the data in the first two columns into a list of lists in the form
[...[2.96738, 0], [3.91727, 1], [3.9729, 0], [4.88419, 1], [4.93686, 0], [5.86113, 1], [5.91125, 0]...]
Running my code:
def Delta_Time_One_State(CleanState):
for counter, value in enumerate(CleanState[1:]):
DeltaT = value[0] - CleanState[counter][0]
Lgt_cut_Time = []
Lgt_Uncut_Time = []
if value[1] == 0:
Lgt_cut_Time.append([value[0] + DeltaT / 2, DeltaT])
else:
Lgt_Uncut_Time.append([value[0] + DeltaT / 2, DeltaT])
clean_state_A = [[0.0, 0], [0.03253, 1], [0.08479, 0], [0.98748, 1], [1.03717, 0], ... [483.8888, 0], [484.6563, 1]]
Delta_Time_One_State(clean_state_A)
gives me
Lgt_Uncut_Time = [[485.04004999999995, 0.7674999999999841]]
Lgt_cut_Time = []
Which can't be right because the for loop runs through almost all of clean_state_A. Since every loop passes through the if statement something appears to be wrong with the .append function but I can't tell what.
Every loop you are redefining the two lists. Move them outside of the for loop so you're appending to the same list every iteration.
def Delta_Time_One_State(CleanState):
Lgt_cut_Time = []
Lgt_Uncut_Time = []
for counter, value in enumerate(CleanState[1:]):
DeltaT = value[0] - CleanState[counter][0]
calculated_data = [value[0] + DeltaT / 2, DeltaT]
if value[1] == 0:
Lgt_cut_Time.append(calculated_data)
else:
Lgt_Uncut_Time.append(calculated_data)
You are recreating the Lgt_cut_Time and Lgt_Uncut_Time lists every loop.
def Delta_Time_One_State(CleanState):
for counter, value in enumerate(CleanState[1:]):
DeltaT = value[0] - CleanState[counter][0]
Lgt_cut_Time = []
Lgt_Uncut_Time = []
if value[1] == 0:
Lgt_cut_Time.append([value[0] + DeltaT / 2, DeltaT])
else:
Lgt_Uncut_Time.append([value[0] + DeltaT / 2, DeltaT])
Just move them outside of the loop so that they accumulate the results instead of replacing them on every loop.
def Delta_Time_One_State(CleanState):
Lgt_cut_Time = []
Lgt_Uncut_Time = []
for counter, value in enumerate(CleanState[1:]):
DeltaT = value[0] - CleanState[counter][0]
if value[1] == 0:
Lgt_cut_Time.append([value[0] + DeltaT / 2, DeltaT])
else:
Lgt_Uncut_Time.append([value[0] + DeltaT / 2, DeltaT])

Start counting indexes from 1 instead of 0 of a list

I created a program to get the the max value of a list and the position of its occurrences (list starting at indexing with 1 not 0) but I can't manage to find any useful solutions.
The input is always a string of numbers divided by zero.
This is my code:
inp = list(map(int,input().split()))
m = max(inp)
count = inp.count(m)
print(m)
def maxelements(seq): # #SilentGhost
return [i for i, j in enumerate(seq) if j == m]
print(maxelements(inp))
I expect to output the maximum value and then all the positions of its occurrences. (also is it possible to do without brackets as in the example below?)
Input: 4 56 43 45 2 56 8
Output: 56
2 6
If you want to shift index values, you could just do
return [i + 1 for i, j in enumerate(seq) if j == m]
more generally any transformation of i or j!
def f(i, j):
# do whatever you want, and return something
return i + 1
return [f(i, j) for i, j in enumerate(seq) if j == m]
Without brackets, as a string:
return " ".join(str(i + 1) for i, j in enumerate(seq) if j==m)
Specifiy start=1 with enumerate():
>>> l = [4, 56, 43, 45, 2, 56, 8]
>>> max_num = max(l)
>>> [i for i, e in enumerate(l, start=1) if e == max_num]
[2, 6]
By default enumerate() uses start=0, because indices start at 0.

How to find median of a list using indexing

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)

What's wrong with this Fibonacci code?

I want to write a Fibonacci sequence code where it takes a number as input and prints that many Fibonacci numbers.
def fibonacci(x):
a = []
a[0] = 0
a[1] = 1
for i in range(2, x + 1):
a[i] = a[i - 1] + a[i - 2]
a += a[i]
return a
a = [] creates an empty array named a. a[0] cannot be instanced because it doesn't exist yet, it raises a out of range error
x = []
x[0] = 0 # <- error
What you need to append it like append() or a+=[] :
def fibonacci(x):
a = []
a.append(0)
a.append(1)
for i in range(2, x + 1):
a.append(a[i - 1] + a[i - 2])
#a +=[a[i - 1] + a[i - 2]]
return a

Resources