read_table in pandas, how to get input from text to a dataframe [duplicate]

六眼飞鱼酱① 提交于 2019-12-04 20:36:03

Maybe pandas can do it but you can do it easily.

data = '''Alabama[edit]
Auburn (Auburn University)[1]
Florence (University of North Alabama)
Jacksonville (Jacksonville State University)[2]
Alaska[edit]
Fairbanks (University of Alaska Fairbanks)[2]
Arizona[edit]
Flagstaff (Northern Arizona University)[6]
Tempe (Arizona State University)
Tucson (University of Arizona)'''

# ---

result = []

state = None

for line in data.split('\n'):

    if line.endswith('[edit]'):
        # remember new state
        state = line[:-6] # without `[edit]`
    else:
        # add state, city to result
        city, rest = line.split(' ', 1)
        result.append( [state, city] )

# --- display ---

for state, city in result:
    print(state, city)

if you read from file then

result = []

state = None

with open('your_file') as f:
    for line in f:
        line = line.strip() # remove '\n'

        if line.endswith('[edit]'):
            # remember new state
            state = line[:-6] # without `[edit]`
        else:
            # add state, city to result
            city, rest = line.split(' ', 1)
            result.append( [state, city] )

# --- display ---

for state, city in result:
    print(state, city)

Now you can use result to create DataFrame.

Using Pandas, you could do the following:

import pandas as pd
df = pd.read_table('data', sep='\n', header=None, names=['town'])
df['is_state'] = df['town'].str.contains(r'\[edit\]')
df['groupno'] = df['is_state'].cumsum()
df['index'] = df.groupby('groupno').cumcount()
df['state'] = df.groupby('groupno')['town'].transform('first')
df['state'] = df['state'].str.replace(r'\[edit\]', '')
df['town'] = df['town'].str.replace(r' \(.+$', '')
df = df.loc[~df['is_state']]
df = df[['state','town']]

which yields

     state          town
1  Alabama        Auburn
2  Alabama      Florence
3  Alabama  Jacksonville
5   Alaska     Fairbanks
7  Arizona     Flagstaff
8  Arizona         Tempe
9  Arizona        Tucson

Here is a breakdown of what the code is doing. After loading the text file into a DataFrame, use str.contains to identify the rows which are states. Use cumsum to take a cumulative sum of the True/False values, where True is treated as 1 and False as 0.

df = pd.read_table('data', sep='\n', header=None, names=['town'])
df['is_state'] = df['town'].str.contains(r'\[edit\]')
df['groupno'] = df['is_state'].cumsum()
#                                               town is_state  groupno
# 0                                    Alabama[edit]     True        1
# 1                    Auburn (Auburn University)[1]    False        1
# 2           Florence (University of North Alabama)    False        1
# 3  Jacksonville (Jacksonville State University)[2]    False        1
# 4                                     Alaska[edit]     True        2
# 5    Fairbanks (University of Alaska Fairbanks)[2]    False        2
# 6                                    Arizona[edit]     True        3
# 7       Flagstaff (Northern Arizona University)[6]    False        3
# 8                 Tempe (Arizona State University)    False        3
# 9                   Tucson (University of Arizona)    False        3

Now for each groupno number, we can assign a unique integer for each row in the group:

df['index'] = df.groupby('groupno').cumcount()
#                                               town is_state  groupno  index
# 0                                    Alabama[edit]     True        1      0
# 1                    Auburn (Auburn University)[1]    False        1      1
# 2           Florence (University of North Alabama)    False        1      2
# 3  Jacksonville (Jacksonville State University)[2]    False        1      3
# 4                                     Alaska[edit]     True        2      0
# 5    Fairbanks (University of Alaska Fairbanks)[2]    False        2      1
# 6                                    Arizona[edit]     True        3      0
# 7       Flagstaff (Northern Arizona University)[6]    False        3      1
# 8                 Tempe (Arizona State University)    False        3      2
# 9                   Tucson (University of Arizona)    False        3      3

Again for each groupno number, we can find the state by selecting the first town in each group:

df['state'] = df.groupby('groupno')['town'].transform('first')
#                                               town is_state  groupno  index          state
# 0                                    Alabama[edit]     True        1      0  Alabama[edit]
# 1                    Auburn (Auburn University)[1]    False        1      1  Alabama[edit]
# 2           Florence (University of North Alabama)    False        1      2  Alabama[edit]
# 3  Jacksonville (Jacksonville State University)[2]    False        1      3  Alabama[edit]
# 4                                     Alaska[edit]     True        2      0   Alaska[edit]
# 5    Fairbanks (University of Alaska Fairbanks)[2]    False        2      1   Alaska[edit]
# 6                                    Arizona[edit]     True        3      0  Arizona[edit]
# 7       Flagstaff (Northern Arizona University)[6]    False        3      1  Arizona[edit]
# 8                 Tempe (Arizona State University)    False        3      2  Arizona[edit]
# 9                   Tucson (University of Arizona)    False        3      3  Arizona[edit]

We basically have the desired DataFrame; all that's left is to prettify the result. We can remove the [edit] from the states and everything after the first parenthesis from the towns using str.replace:

df['state'] = df['state'].str.replace(r'\[edit\]', '')
df['town'] = df['town'].str.replace(r' \(.+$', '')

Remove the rows where the town is actually a state:

df = df.loc[~df['is_state']]

And finally, keep only the desired columns:

df = df[['state','town']]
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!