Alejandro A
Alejandro A

Reputation: 1190

Map value to a column if key isin 'value'

I have a dict

{'Spain':'34',
'Chile':'56',
'China':861'}

And a pandas dataframe:

| id | phone |
--------------
|  1 | 343123|
|  2 | 111111|
|  3 | 861231|
|  4 | 86911 |
|  5 | 56441 |

I want to map the dictionary to a new column the key if 'phone' startswith the value.

| id | phone | country |
------------------------
|  1 | 343123|   Spain |
|  2 | 111111|   None  |
|  3 | 861231|   China |
|  4 | 86911 |   None  |
|  5 | 56441 |   Chile |

RELEVANT; DICTIONARY ORDER COULD BE REVERSED

Upvotes: 0

Views: 697

Answers (2)

Dani Mesejo
Dani Mesejo

Reputation: 61920

You could do:

lookup = {'Spain': '34',
          'Chile': '56',
          'China': '861'}

reverse = { v: k  for k, v in lookup.items()}

df['country'] = df['phone'].astype(str)\
    .str.extract(fr'^({"|".join(reverse.keys())})')\
    .squeeze().map(reverse)
print(df)

Output

   id   phone country
0   1  343123   Spain
1   2  111111     NaN
2   3  861231   China
3   4   86911     NaN
4   5   56441   Chile

Upvotes: 1

Tom Ron
Tom Ron

Reputation: 6181

You can pandas' apply -

def my_func(x, my_dict):
    for k, v in my_dict.items():
        if x.startswith(v):
            return k
    return None

my_dict = {
    'Spain':'34',
    'Chile':'56',
    'China':'861'}

df['phone'].apply(lambda x: my_func(x, my_dict))

Since there is prefixes may overlap, I suggest using an ordered data structure, e.g list, see below. The code will require slight modification.

prefixes = [('Spain', '34'), ('Chile', '56'), ('China', '861')]

Upvotes: 1

Related Questions