9. 웹의 다양한 형식


파이썬을 이용한 머신러닝, 딥러닝 실전개발 입문

파이썬을 이용한 머신러닝, 딥러닝 실전개발 입문 책과 강의를 바탕으로한 코드 리뷰 및 정리입니다. 자세한 내용은 책과 강의를 참고해주세요.


3. 데이터 소스의 서식과 가공

3-1. 웹의 다양한 데이터 형식

1.XML

2.JSON

3.CSV

4.Excel


텍스트 데이터와 바이너리 데이터
  • 텍스트 데이터 - 텍스트 에디터로 편집할 수 있는 데이터 포맷. 가독성이 높음.

    • 자연언어(한국어, 영어 등), 숫자, 제어문자(줄바꿈, 탭 등), 프로그래밍 언어의 소스코드, XML/JSON/CSV 등 웹에서 주로 사용하는 데이터 포맷
  • 바이너리 데이터 - 텍스트 데이터 이외의 데이터들. 문자에 할당되는 영역 외의 영역도 사용하므로 텍스트 에디터로 열 수 없음. 시각적으로 확인해도 의미를 알 수 없는 문자열로 표시. 크기가 작음.


    #바이너리로 '100'데이터 저장
    filename="a.bin"
    data=100
      
    with open(filename, "wb") as f:
        f.write(bytearray([data]))
          
    

    바이너리 데이터로 100을 표현하는데는 1바이트 뿐이 들지 않는다. (텍스트 데이터는 3바이트.) 따라서 보다 효율적으로 저장할 수 있는 데이터 형식.


    오늘날의 CPU가 좋아 사실상 속도에는 큰 차이가 없지만 이미지와 동영상과 같은 압축이 필요한 파일들 때문에 웹상에서는 바이너리 형식의 데이터가 더 많이 사용된다.


텍스트 데이터의 주의점

어떤 문자 인코딩으로 저장돼있냐에 따라 다른 의미를 가진다. 최근 텍스트 데이터를 기반으로 하는 데이터는 ‘UTF-8’로 인코딩 되어 있다. 하지만 한국에선 아직도 ‘EUC_KR’을 사용하는 경우가 많아 주의가 필요하다.



1. XML 분석
  • XML : HTML 형식으로 나타낸 데이터 구조. 텍스트 데이터를 기반으로 하며 태그를 이용해 데이터를 계층 구조로 표현할 수 있다.


  • XML의 기본적인 구조

    • 태그 <태그> : 여는 태그

      : 닫는태그

      루트태그는 하나여야 한다.

    • 요소(Element)

      1. <태그>
      2. <태그 />
    • 콘텐츠

      ex) <태그></태그>
          <태그>
              <태그></태그>
              <태그></태그>
          </태그>
      
    • 속성

      ex) <태그 속성="값" 속성="값" 속성="값" 속성="값"></태그>
          
      ex) <태그 속성="값" 속성="값" 속성="값" 속성="값" />
      


      예시

      <intro time="아침">안녕하세요</intro>
      <body>
          <first time="밤">안녕히주무세요</first>
          <second eat="식사">맛있게드세요</second>
      </body>
          
          
      
      • intro, body, first, second : 태그
      • time, eat : 속성
      • 아침, 밤, 식사 : 값


  • 파이썬으로 XML 분석 - 날씨 분류

    url을 불러오면 다음과 같다.

    <?xml version="1.0" encoding="utf-8" ?>
    <rss version="2.0">
    <channel>
    <title>기상청 육상 중기예보</title>
    <link>http://www.kma.go.kr/weather/forecast/mid-term_01.jsp</link>
    <description>기상청 날씨 웹서비스</description>
    <language>ko</language>
    <generator>기상청</generator>
    <pubDate>2018년 10월 11일 (목)요일 06:00</pubDate>
     <item>
    <author>기상청</author>
    <category>육상중기예보</category>
    <title>전국 육상 중기예보 - 2018년 10월 11일 (목)요일 06:00 발표</title>
    <link>http://www.kma.go.kr/weather/forecast/mid-term_01.jsp</link>
    <guid>http://www.kma.go.kr/weather/forecast/mid-term_01.jsp</guid>
    <description>
    	<header>
    		<title>전국 육상중기예보</title>
    		<tm>201810110600</tm>
    		<wf><![CDATA[이번 예보기간에는 고기압의 영향으로 대체로 맑은 날이 많겠습니다.<br />기온은 평년(최저기온: 3~15℃, 최고기온: 17~23℃)과 비슷하거나 조금 낮겠습니다. <br />강수량은 평년(0~5mm)보다 적겠습니다.<br /><br />* 대체로 맑은 날씨가 이어지면서 대기가 건조하겠으니, 화재예방에 각별히 유의하기 바랍니다.]]></wf>
    	</header>
    	<body>
      				
      
    		<location wl_ver="3">
    				<province>서울ㆍ인천ㆍ경기도</province>
    				<city>서울</city>
      				
    				<data>
    					<mode>A02</mode>
    					<tmEf>2018-10-14 00:00</tmEf>
    					<wf>구름조금</wf>
    					<tmn>8</tmn>
    					<tmx>20</tmx>
    					<reliability>보통</reliability>
    				</data>
                  
                ...
    


    파이썬으로 날씨별로 어떤 지역이 해당되는지 구분해 본다.

    from bs4 import BeautifulSoup
    import urllib.request as req
    import os.path
      
    url="http://www.kma.go.kr/weather/forecast/mid-term-rss3.jsp?stnId=108"
    savename="forecast.xml"
    if not os.path.exists(savename):
        req.urlretrieve(url,savename)
          
    xml=open(savename, "r", encoding="utf-8").read()
    soup=BeautifulSoup(xml,'html.parser')
      
    #날씨 별 도시로 dict 생성
    info={}
    for location in soup.find_all("location"):
        name=location.find('city').string
        weather=location.find('wf').string
        if not (weather in info):
            info[weather]=[]
        info[weather].append(name)
          
    for weather in info.keys():
        print("+", weather)
        for name in info[weather]:
            print("|-", name)
    



2. JSON 분석
  • JSON : JavaScript Object Notation. 자바스크립트에서 사용하는 객체 표기 방법을 기반으로 한다. 텍스트 기반으로 하는 가벼운 데이터 형식이며 구조가 단순하다는 것이 장점. 따라서 많은 웹 API들이 JSON 형식으로 데이터를 제공한다. 참고


  • JSON의 구조

    자료형표현 방법사용 예
    숫자숫자30, 23.5
    문자열””“str”, “123”
    true / false (소문자)true
    배열[n1, n2, n3, …][1, 2, 10, “안녕”, true]
    객체{“key”:value, “key”:value, …}{“org” : 50, “com” : “값”, “sho” : true, “mic” : [1,59], “alw” : { “name” : 52 } }
    nullnullnull


  • 파이썬으로 JSON 분석

    JSON은 다음과 같이 구성되어 있다

    [
      {"name":"사과","price":"1000"},
      {"name":"바나나","price":"2000"},
      {"name":"배","price":"3000"},
      {"name":"귤","price":"4000"},
      {"name":"자두","price":"5000"}
                  
    ]
    


    다음과 같이 파이썬 list와 JSON을 마음대로 변환시킬 수 있다.

    import json
      
    jsonData="""[
      {"name":"사과","price":"1000"},
      {"name":"바나나","price":"2000"},
      {"name":"배","price":"3000"},
      {"name":"귤","price":"4000"},
      {"name":"자두","price":"5000"}
                  
    ]"""
      
    #JSON 문자열 -> 파이썬 자료형
    output=json.loads(jsonData)
    print(type(output)) #list
    print(output)
      
    #파이썬 자료형 -> JSON 문자열
    text=json.dumps(output)
    print(type(text)) #str
    print(text)
    


    파이썬으로 JSON파일을 불러와 분석해 본다.

    import urllib.request as req
    import os.path, random
    import json
      
    url="https://api.github.com/repositories"
    savename="repo.json"
    if not os.path.exists(savename):
        req.urlretrieve(url, savename)
          
    jsonData=open(savename, "r", encoding="utf-8")    
    items=json.loads(jsonData)
    for item in items:
        print(item["name"]+"-"+item["owner"]["login"])
    


  • JSON 형식으로 출력하기

    • 파이썬의 딕셔너리와 리스트의 작성방법과 동일하다
    import json
    price={
        "date":"2018-10-11",
        "price":{
            "Apple":80,
            "Orange":55,
            "Banana":40
        }
    }
    jsonData=json.dumps(price)
    print(jsonData)
    



3. CSV 분석
  • csv : Comma-Separated Values. 각 필드를 쉼표로 구분. 텍스트 에디터를 사용해 간편히 수정 가능. 형식이 단순하다. 엑셀에서 CSV형식으로 export 할 때 각 국가의 언어코드로 출력되니 사용할 때 인코딩이 꼬이지 않게 조심해야 한다.
  • TSV : Tab- Separated Values / SSV : Space-Separated Values 도 있으나 주로 통칭해서 CSV형식이라고 말한다.


  • CSV 구조

    1. 1줄에 데이터 하나, 한 줄에는 쉼표로 속성 구분

      1000, 비누, 300
      1001, 장갑, 150
      1002, 마스크, 230
      
    2. 첫 번째 줄은 Header로 사용 가능

      ID, 이름, 가격
      1000, 비누, 300
      1001, 장갑, 150
      1002, 마스크, 230
    


  • CSV 파일 읽기

    다음과 같은 CSV파일이 있다고 하자.

    ID,이름,가격
    1000,비누,300
    1001,장갑,150
    1002,마스크,230
    
    import csv, codecs #codecs : 인코딩 변환
      
    #EUC_KR로 저장된 csv파일 읽기
    filename="list-euckr.csv"
    file=codecs.open(filename, "r", "euc_kr")
    csv=csv.reader(file, delimiter=",", quotechar='"') #delimiter(구분문자), quotechar(어떤 기호로 데이터를 감싸고 있는지)
      
    for cell in csv:
        print(cell[1],cell[2])
    


  • CSV파일 쓰기

    • csv.writer() 사용
    import csv,codecs
      
    with codecs.open("test.csv","w","euc_kr") as fp:
        writer=csv.writer(fp, delimiter=",", quotechar='"')
        writer.writerow(["ID","이름","가격"])
        writer.writerow(["1000","SD카드","30000"])
        writer.writerow(["1001","키보드","21000"])
        writer.writerow(["1002","마우스","15000"])
    



4.엑셀 분석
  • 엑셀 파일의 구조
    • 북(book) : 여러개의 시트(sheet)로 구성된 것
    • 시트(sheet) : 행(row)과 열(column)으로 구성된 2차원 셀(cell)


  • 파이썬으로 엑셀 분석

    import openpyxl
      
    #엑셀 파일 열기
    filename="stat_104102.xlsx"
    book=openpyxl.load_workbook(filename)
      
    #맨 앞 시트 추출
    sheet=book.worksheets[0]
      
    #시트의 각 행을 순서대로 추출하기
    data=[]
    for row in sheet.rows:
        data.append([
            row[0].value,
            row[9].value
        ])
      
    #필요없는 줄(헤더, 연도, 계 ) 제거
    del data[0]
    del data[1]
    del data[2]
      
    #데이터를 인구 순서대로 정렬
    data=sorted(data,key=lambda x:x[1])
      
    #하위 5위를 출력
    for i, a in enmerate(data):
        if(i>=5):
            break
        print(i+1, a[0], int(a[1]))
    


  • 파이썬으로 엑셀 쓰기

    #엑셀 쓰기
    import openpyxl
      
    workbook=openpyxl.Workbook()
    sheet=workbook.active
      
    sheet["A1"]="테스트 파일"
    sheet["A2"]="안녕하세요"
    sheet.merge_cells("A1:C1")
    sheet["A1"].font = openpyxl.styles.Font(size=20, color="FF0000")
      
    #데이터 쓰기
    workbook.save("newFile.xlsx")
    


  • Pandas를 이용해 엑셀 파일을 읽기

    import pandas as pd
      
    filename="stat_104102.xlsx"
    sheet_name="stat_104102"
    book=pd.read_excel(filename, sheetname=sheet_name, header=1) #첫번째 줄부터 헤더
      
    #2015 인구로 정렬
    book=book.sort_value(by=2015, ascending=False)
    print(book)
    






© 2018. by yeo0

Powered by yeo0