programing

Python Pandas - 여러 테이블이 포함된 csv 파일 읽기

starjava 2023. 10. 9. 21:15
반응형

Python Pandas - 여러 테이블이 포함된 csv 파일 읽기

싱글이 있습니다..csv여러 테이블을 포함하는 파일입니다.

Panda를 사용하면 두 개의 DataFrame을 얻을 수 있는 가장 좋은 전략은 무엇입니까?inventory그리고.HPBladeSystemRack이 파일에서?

인풋.csv다음과 같습니다.

Inventory       
System Name            IP Address    System Status
dg-enc05                             Normal
dg-enc05_vc_domain                   Unknown
dg-enc05-oa1           172.20.0.213  Normal

HP BladeSystem Rack         
System Name               Rack Name   Enclosure Name
dg-enc05                  BU40  
dg-enc05-oa1              BU40        dg-enc05
dg-enc05-oa2              BU40        dg-enc05

제가 지금까지 생각해낸 최선의 방법은 이것을 전환하는 것입니다..csvExcel 워크북에 파일 저장(xlxs), 테이블을 시트로 나누어 사용합니다.

inventory = read_excel('path_to_file.csv', 'sheet1', skiprow=1)
HPBladeSystemRack = read_excel('path_to_file.csv', 'sheet2', skiprow=2)

단,

  • 이 접근 방식은 다음을 요구합니다.xlrd모듈.
  • 로그 파일은 실시간으로 분석해야 하므로 로그에서 가져온 파일을 분석하는 방법을 찾는 것이 훨씬 좋습니다.
  • 실제 로그에는 테이블이 두 개보다 훨씬 많습니다.

테이블 이름을 미리 알고 있다면 다음과 같은 것이 있습니다.

df = pd.read_csv("jahmyst2.csv", header=None, names=range(3))
table_names = ["Inventory", "HP BladeSystem Rack", "Network Interface"]
groups = df[0].isin(table_names).cumsum()
tables = {g.iloc[0,0]: g.iloc[1:] for k,g in df.groupby(groups)}

키를 테이블 이름으로 하고 값을 하위 테이블로 하는 사전을 만들기 위해 작업해야 합니다.

>>> list(tables)
['HP BladeSystem Rack', 'Inventory']
>>> for k,v in tables.items():
...     print("table:", k)
...     print(v)
...     print()
...     
table: HP BladeSystem Rack
              0          1               2
6   System Name  Rack Name  Enclosure Name
7      dg-enc05       BU40             NaN
8  dg-enc05-oa1       BU40        dg-enc05
9  dg-enc05-oa2       BU40        dg-enc05

table: Inventory
                    0             1              2
1         System Name    IP Address  System Status
2            dg-enc05           NaN         Normal
3  dg-enc05_vc_domain           NaN        Unknown
4        dg-enc05-oa1  172.20.0.213         Normal

열 이름을 첫 번째 행 등으로 설정할 수 있습니다.

당신이 분석하고 싶은 테이블의 이름을 알고 있다고 가정합니다.csv파일입니다. 만약 그렇다면, 당신은 당신이 그를index각각의 위치를 선택하고, 그에 따라 해당 슬라이스를 선택합니다.스케치로서, 다음과 같이 나타낼 수 있습니다.

df = pd.read_csv('path_to_file')    
index_positions = []
for table in table_names:
    index_positions.append(df[df['col_with_table_names']==table].index.tolist()[0])

## Include end of table for last slice, omit for iteration below
index_positions.append(df.index.tolist()[-1])

tables = {}
for position in index_positions[:-1]:
    table_no = index_position.index(position)
    tables[table_names[table_no] = df.loc[position:index_positions[table_no+10]]

확실히 더 우아한 해결책들이 있지만, 이것은 당신에게 다음을 제공할 것입니다.dictionary표명을 다음과 같이 하여keys및 해당 표는 다음과 같습니다.values.

팬더들은 이것을 쉽게 할 준비가 되어있지 않은 것 같아 결국 저는 제 자신을 하게 되었습니다.split_csv기능.테이블 이름만 필요하고 출력됩니다..csv각 테이블의 이름을 딴 파일입니다.

import csv
from os.path import dirname # gets parent folder in a path
from os.path import join # concatenate paths

table_names = ["Inventory", "HP BladeSystem Rack", "Network Interface"]

def split_csv(csv_path, table_names):
    tables_infos = detect_tables_from_csv(csv_path, table_names)
    for table_info in tables_infos:
        split_csv_by_indexes(csv_path, table_info)

def split_csv_by_indexes(csv_path, table_info):
    title, start_index, end_index = table_info
    print title, start_index, end_index
    dir_ = dirname(csv_path)
    output_path = join(dir_, title) + ".csv"
    with open(output_path, 'w') as output_file, open(csv_path, 'rb') as input_file:
        writer = csv.writer(output_file)
        reader = csv.reader(input_file)
        for i, line in enumerate(reader):
            if i < start_index:
                continue
            if i > end_index:
                break
            writer.writerow(line)

def detect_tables_from_csv(csv_path, table_names):
    output = []
    with open(csv_path, 'rb') as csv_file:
        reader = csv.reader(csv_file)
        for idx, row in enumerate(reader):
            for col in row:
                match = [title for title in table_names if title in col]
                if match:
                    match = match[0] # get the first matching element
                    try:
                        end_index = idx - 1
                        start_index
                    except NameError:
                        start_index = 0
                    else:
                        output.append((previous_match, start_index, end_index))
                    print "Found new table", col
                    start_index = idx
                    previous_match = match
                    match = False

        end_index = idx  # last 'end_index' set to EOF
        output.append((previous_match, start_index, end_index))
        return output


if __name__ == '__main__':
    csv_path = 'switch_records.csv'
    try:
        split_csv(csv_path, table_names)
    except IOError as e:
        print "This file doesn't exist. Aborting."
        print e
        exit(1)

언급URL : https://stackoverflow.com/questions/34184841/python-pandas-read-csv-file-containing-multiple-tables

반응형