Update dataframe via for loop - python

The code below has to update test_df dataframe, which is currently filled with NaNs.
Each 'dig' (which is always an integer) value has corresponding 'top', 'bottom', 'left' and 'right' values, and the slices of dataframe, corresponding to respective top:bottom, left:right ranges for each 'dig', need to be updated with 'dig' values.
For example, if dig=9, top=2, botton=4, left=1 and right=5, all the NaNs within the range of 2:4, 1:5 need to be replaced with 9s.
The following code reports no errors, however, no NaNs are being updated.
for index, row in letters_df.iterrows():
dig = str(row[0])
top = int(height) - int(row[2])
bottom = int(height) - int(row[4])
left = int(row[1])
right = int(row[3])
test_df.iloc[top:bottom, left:right] = dig
test_df:
0 1 2 3 4 5 6 ... 633 634 635 636 637 638 639
0 NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN
1 NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN
2 NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN
3 NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN
4 NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN
letters_df:
0 1 2 3 4 5 dig_unique_letters
0 T 36 364 51 388 0 0
1 h 36 364 55 388 0 1
2 i 57 364 71 388 0 2
3 s 76 364 96 388 0 3
4 i 109 364 112 388 0 2

The problem I see is that in letters_df the value in column 4 is higher than the value in column 2. That means that when you do top = int(height) - int(row[2])
bottom = int(height) - int(row[4]) the value you will get in top will be bigger than the value you will get in bottem. So when you index .iloc[top:bottom] you have no rows in the slice. Maybe you should switch between top and bottem.

Related

Iterating like tree method in pandas

Input :
Expected Output :
LEVEL LEVEL-1 LEVEL-2 LEVEL-3 LEVEL-4 LEVEL-5 LEVEL-6 Value Result Explanation
0 1 A01 NaN NaN NaN NaN NaN 10 550 = I3 + H2
1 2 NaN A011 NaN NaN NaN NaN 20 540 = I4 + H3
2 3 NaN NaN AO111 NaN NaN NaN 30 520 = I5 + H4
3 4 NaN NaN NaN A01111 NaN NaN 40 490 = I6 + i9 + H5
4 5 NaN NaN NaN NaN AO11111 NaN 50 180 = I8 + I7 + H6
5 6 NaN NaN NaN NaN NaN AO111111 60 60 = H7
6 6 NaN NaN NaN NaN NaN AO111112 70 70 = H8
7 5 NaN NaN NaN NaN AO11112 NaN 80 270 = I11+I10+H9
8 6 NaN NaN NaN NaN NaN AO111121 90 90 = H10
9 6 NaN NaN NaN NaN NaN AO111122 100 100 = H11
Explanation:
I have to get the Result column on the basis of Explanation Column. This Explanation column is made on basis Tree type. For example AO111121 & AO111122 are children's of its immediate parent AO11112 so AO11112 = AO111121 + AO111122 + AO11112 accordingly.
You could do
# Consolidating nodes and finding parents
df["Node"] = df["LEVEL-1"]
for level in range(2, 7):
col, last_col = df[f"LEVEL-{level}"], df[f"LEVEL-{level - 1}"]
df.loc[col.notna(), "Node"] = col
df.loc[col.notna(), "Parent"] = last_col.ffill()
df = df.drop(columns=[col for col in df.columns if col.startswith("LEVEL-")])
# Identifying childs
df = df.merge(
df.Node.groupby(df.Parent).apply(set).rename("Childs"),
left_on="Node", right_on="Parent", how="left"
)
# Recursively adding up results
def result(childs):
return df.loc[df.Node.isin(childs), "Result"].sum()
df["Result"] = df.Value
for level in range(5, 0, -1):
add_results = df.loc[df.LEVEL.eq(level), "Childs"].map(result)
df.loc[df.LEVEL.eq(level), "Result"] += add_results
Result for df
LEVEL LEVEL-1 LEVEL-2 LEVEL-3 LEVEL-4 LEVEL-5 LEVEL-6 Value Result_exp
0 1 A01 NaN NaN NaN NaN NaN 10 550
1 2 NaN A011 NaN NaN NaN NaN 20 540
2 3 NaN NaN AO111 NaN NaN NaN 30 520
3 4 NaN NaN NaN A01111 NaN NaN 40 490
4 5 NaN NaN NaN NaN AO11111 NaN 50 180
5 6 NaN NaN NaN NaN NaN AO111111 60 60
6 6 NaN NaN NaN NaN NaN AO111112 70 70
7 5 NaN NaN NaN NaN AO11112 NaN 80 270
8 6 NaN NaN NaN NaN NaN AO111121 90 90
9 6 NaN NaN NaN NaN NaN AO111122 100 100
is
LEVEL Value Result_exp Node Parent Childs Result
0 1 10 550 A01 NaN {A011} 550
1 2 20 540 A011 A01 {AO111} 540
2 3 30 520 AO111 A011 {A01111} 520
3 4 40 490 A01111 AO111 {AO11111, AO11112} 490
4 5 50 180 AO11111 A01111 {AO111111, AO111112} 180
5 6 60 60 AO111111 AO11111 NaN 60
6 6 70 70 AO111112 AO11111 NaN 70
7 5 80 270 AO11112 A01111 {AO111122, AO111121} 270
8 6 90 90 AO111121 AO11112 NaN 90
9 6 100 100 AO111122 AO11112 NaN 100
Be aware that in the dataframe you've provided you're using 0 and O inconsistently.

Iterating through multiple elements of a single list in python

I have a dataset that looks like below:
Zn Pb Ag Cu Mo Cr Ni Co Ba
87 7 0.02 42 2 57 38 14 393
70 6 0.02 56 2 27 29 20 404
75 5 0.02 69 2 44 23 17 417
70 6 0.02 54 1 20 19 12 377
I want to create a pandas dataframe out of this dataset. I have written the function below:
def correlation_iterated(raw_data,element_concentration):
columns = element_concentration.split()
df1 = pd.DataFrame(columns=columns)
data1=[]
selected_columns = raw_data.loc[:, element_concentration.split()].columns
for i in selected_columns:
for j in selected_columns:
# another function that takes 'i' and 'j' and returns 'a'
zipped1 = zip([i], a)
data1.append(dict(zipped1))
df1 = df1.append(data1,True)
print(df1)
This function is supposed to do the calculations for each element and create a 9 by 9 pandas dataframe and store each calculation in each cell. But I get the following:
Zn Pb Ag Cu Mo Cr Ni Co Ba
0 1.000000 NaN NaN NaN NaN NaN NaN NaN NaN
1 0.460611 NaN NaN NaN NaN NaN NaN NaN NaN
2 0.127904 NaN NaN NaN NaN NaN NaN NaN NaN
3 0.276086 NaN NaN NaN NaN NaN NaN NaN NaN
4 -0.164873 NaN NaN NaN NaN NaN NaN NaN NaN
.. ... .. .. .. .. .. .. .. ...
76 NaN NaN NaN NaN NaN NaN NaN NaN 0.113172
77 NaN NaN NaN NaN NaN NaN NaN NaN 0.027251
78 NaN NaN NaN NaN NaN NaN NaN NaN -0.036409
79 NaN NaN NaN NaN NaN NaN NaN NaN 0.041396
80 NaN NaN NaN NaN NaN NaN NaN NaN 1.000000
[81 rows x 9 columns]
which is basically calculating the results of the first column and storing them in just the first column, then doing the calculations and appending new rows to the column. How can I program the code in a way that appends new calculations to the next column when finished with one column? I want sth like this:
Zn Pb Ag Cu Mo Cr Ni Co Ba
0 1.000000 0.460611 ...
1 0.460611 1.000000 ...
2 0.127904 0.111559 ...
3 0.276086 0.303925 ...
4 -0.164873 -0.190886 ...
5 0.402046 0.338073 ...
6 0.174774 0.096724 ...
7 0.165760 -0.005301 ...
8 -0.043695 0.174193 ...
[9 rows x 9 columns]
Could you not just do something like this:
def correlation_iterated(raw_data,element_concentration):
columns = element_concentration.split()
data = {}
selected_columns = raw_data.loc[:,columns].columns
for i in selected_columns:
temp = []
for j in selected_columns:
# another function that takes 'i' and 'j' and returns 'a'
temp.append(a)
data[i] = temp
df = pd.DataFrame(data)
print(df)

How convert rows in a list using pandas

Used code and file: https://github.com/CaioEuzebio/Python-DataScience-MachineLearning/tree/master/SalesLogistics
I am working on an analysis using pandas. Basically I need to sort the orders by quantity of products, and containing the same products.
Example: I have order 1 and order 2, both have product A and product B. Using the product list and product quantity as a key I will create a pivot that will index this combination of products and return me the order who own the same products.
The general objective of the analysis is to obtain a dataframe as follows:
dfFinal
listProds Ordens NumProds
[prod1,prod2,prod3] 1 3
2
3
[prod1,prod3,prod5] 7 3
15
25
[prod5] 8 1
3
So far the code looks like this.
Setting the 'Order' column as index so that the first pivot is made.
df1.index=df1['Ordem']
df3 = df1.assign(col=df1.groupby(level=0).Produto.cumcount()).pivot(columns='col', values='Produto')
With this pivot I get the dataframe below.
df3 =
col 0 1 2 3 4 5 6 7 8 9 ... 54 55 56 57 58 59 60 61 62 63
Ordem
10911KD YIZ12FF-A YIZ12FF-A YIIE2FF-A YIR72FF-A YIR72FF-A YIR72FF-A NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN
124636 HYY32ZY-A HYY32ZY-A NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN
1719KD5 YI742FF-A YI742FF-A YI742FF-A YI742FF-A NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN
22215KD YI762FF-A YI762FF-A YI762FF-A YI762FF-A YI762FF-A YI762FF-A YI6E2FF-A YI6E2FF-A YI6E2FF-A NaN ... NaN NaN NaN NaN NaN
When I finish running the code, NaN values ​​appear, and I need to remove them from the lines so that I don't influence the analysis I'm doing.

Pandas read text file with special regex

I need to get ad dataframe from files built up like this:
MANDT#|#BWKEY#|#BUKRS#|#BWMOD#|#XBKNG#|#MLBWA#|#MLBWV#|#XVKBW
150#|#2000#|#1001#|##|##|##|##|#
150#|#2001#|#1001#|##|##|##|##|#
150#|#2002#|#1001#|##|##|##|##|#
150#|#4000#|#1000#|##|##|##|##|#
150#|#4001#|#1000#|##|##|##|##|#
150#|#4002#|#1000#|##|##|##|##|#
150#|#4003#|#1000#|##|##|##|##|#
150#|#4005#|#1000#|##|##|##|##|#
What would be the right python regex for separation (#|#) in read_csv?
Thank´s!
Escape the vertical bar, which has a special meaning, with \|
df = pd.read_clipboard(sep=r'#\|#')
print(df)
MANDT BWKEY BUKRS BWMOD XBKNG MLBWA MLBWV XVKBW
0 150 2000 1001 NaN NaN NaN NaN NaN
1 150 2001 1001 NaN NaN NaN NaN NaN
2 150 2002 1001 NaN NaN NaN NaN NaN
3 150 4000 1000 NaN NaN NaN NaN NaN
4 150 4001 1000 NaN NaN NaN NaN NaN
5 150 4002 1000 NaN NaN NaN NaN NaN
6 150 4003 1000 NaN NaN NaN NaN NaN
7 150 4005 1000 NaN NaN NaN NaN NaN

Python Groupby omitting columns

I have a dataframe that looks like this
dg:
thing1 thing2 thing3 thing4 thing5 thing6 thing7 ID
NAN 1 NAN NAN NAN NAN NAN 222
NAN NAN 3 NAN NAN NAN NAN 222
NAN NAN NAN 2 NAN NAN NAN 222
3 NAN NAN NAN NAN NAN 3 222
NAN NAN NAN NAN NAN NAN NAN 222
NAN NAN NAN NAN 4 NAN NAN 222
NAN NAN NAN NAN NAN 4 NAN 222
NAN 3 NAN 2 NAN NAN NAN 555
NAN NAN 3 NAN NAN NAN NAN 555
NAN NAN NAN NAN NAN NAN NAN 555
when I do a groupby like this:
dg = dg.groupby('ID').max().reset_index()
it produces the following ouput, omitting two columns, like this:
ID thing2 thing3 thing4 thing5 thing7
222 1 3 2 4 3
555 3 2
The dataframe follows that pattern but I don't know why two columns are being omitted
NAN values are np.nan
I found out I had a string "N/A" value in the midst of my np.nan values. Lesson is strings with integers can cause columns to disappear when doing groupby functions. The columns that didn't have "N/A" string didn't disappear upon doing groupby functions. When I replaced "N/A" strings with np.nan the columns didn't disappear when I did the groupby

Categories

Resources