Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Map values based off matched columns - Python

I want to map values based how two columns are matched. For instance, the df below contains different labels, A or B. I want to assign a new column that describes these labels. How this occurs is comparing columns Z L and Z P. Z L will always contain either ['X1','X2','X3','X4']. While Z P will correspondingly contain ['LA','LB','LC','LD'].

These will always be in acceding order or reverse order. As in ascending order will mean X1 corresponds to LA, X2 corresponds to LB etc. Reverse order means X1 corresponds to LD, X2 corresponds to LC etc.

If ascending order I want to map an R. If reverse order I want to map an L.

X = ['X1','X2','X3','X4']

R = ['LA','LB','LC','LD']
L = ['LD','LC','LB','LA']

df = pd.DataFrame({
        'Period' : [1,1,1,1,1,2,2,2,2,2],        
        'labels' : ['A','B','A','B','A','B','A','B','A','B'],                  
        'Z L' : [np.nan,np.nan,'X3','X2','X4',np.nan,'X2','X3','X3','X1'],     
        'Z P' : [np.nan,np.nan,'LC','LC','LD',np.nan,'LC','LC','LB','LA'],                       
        })

df = df.dropna()

This is the output dataset to determine the combinations. I have a large df with repeated combinations so I'm not too concerned with returning all of them. I'm mainly concerned with all unique Mapped values for each Period.

   Period labels Z L Z P
2       1      A  X3  LC
3       1      B  X2  LC
4       1      A  X4  LD
6       2      A  X2  LC
7       2      B  X3  LC
8       2      A  X3  LB
9       2      B  X1  LA

Attempt:

labels = df['labels'].unique().tolist()

I = df.loc[df['labels'] == labels[0]]
J = df.loc[df['labels'] == labels[1]]


I['Map'] = ((I['Z L'].isin(X)) | (I['Z P'].isin(R))).map({True:'R', False:'L'})

J['Map'] = ((J['Z L'].isin(X)) | (J['Z P'].isin(R))).map({True:'R', False:'L'})

If I drop duplicates from period and labels the intended df is:

   Period labels    Map
0       1      A      R
1       1      B      L
2       2      A      L
3       2      B      R
like image 252
jonboy Avatar asked Jan 31 '26 18:01

jonboy


1 Answers

Here's my approach:

# the ascending orders
lst1,lst2 = ['X1','X2','X3','X4'], ['LA','LB','LC','LD']

# enumerate the orders
d1, d2 = ({v:k for k,v in enumerate(l)} for l in (lst1, lst2))

# check if the enumerations in `Z L` and `Z P` are the same
df['Map'] = np.where(df['Z L'].map(d1)== df['Z P'].map(d2), 'R', 'L')

Output:

   Period labels Z L Z P Map
2       1      A  X3  LC   R
3       1      B  X2  LC   L
4       1      A  X4  LD   R
6       2      A  X2  LC   L
7       2      B  X3  LC   R
8       2      A  X3  LB   L
9       2      B  X1  LA   R

and df.drop_duplicates(['Period', 'labels']):

   Period labels Z L Z P Map
2       1      A  X3  LC   R
3       1      B  X2  LC   L
6       2      A  X2  LC   L
7       2      B  X3  LC   R
like image 78
Quang Hoang Avatar answered Feb 03 '26 07:02

Quang Hoang