🤔 지난주 과제

  • 파이썬 라이브러리를 활용한 머신러닝 구매
  • Kaggle 승급하기
  • Jupyter, colab 노트북 생성
  • 파이썬 라이브러리를 활용한 머신러닝 github clone
  • 백준, 프로그래머스 가입



1주차 우리가 한 것은..

9월 14일 ML은 1주차로 “Numpy와 Pandas”에 대해 알아보는 시간을 가졌습니다!
3시간.. 동안 ppt와 코드를 보면서 발표를 듣고 마지막에 복습 겸 퀴즈를 풀며 스터디를 마무리했습니다!

서론

Numpy와 Pandas에 대해 알아보기 전에 파이썬 머신러닝 생태계를 구성하는 주요 패키지에 대해서 알아보았습니다!

  • 머신러닝 패키지 : scikit-learn
    ▫ 오픈소스 머신러닝 라이브러리
    ▫ Numpy, Scipy, Matplotlib 기반으로 생성
    머신러닝의 주요 알고리즘/모듈(분류/회귀/클러스터링 등)이 구현되어 있는 라이브러리 (단, 딥러닝 모듈 없음! )

    cf) 딥러닝 패키지 : TensorFlow, Keras, PyTorch
    00. 사이킷런(scikit-learn)이란
    [python] scikit-learn이란

  • 배열/선형대수/통계 패키지
    numpy : 제일 중요! / 배열과 선형대수를 위한 패키지 / Numpy를 기반으로 해서 많은 머신러닝 패키지들이 만들어져 있음!
    SciPy : 파이썬의 대표적인 통계 패키지 / 희소행렬과 같은 자연과학에서 많이 사용되는 유틸리티가 담겨있음!

  • 데이터 핸들링 : pandas
    ▫ 2차원 데이터를 핸들링 == 행과 열로 이루어진 정형 데이터를 가공, 변환
    cf) Numpy도 데이터 핸들링 가능 → but 저차원 API라 pandas에 비해 개발 생산성이 떨어짐

  • 데이터 시각화 : matplotlib
    ▫ 데이터의 직관적 이해, 시각적인 표현을 위한 라이브러리 / 많은 다른 시각화 솔루션들이 matplotlib을 기반으로 만들어짐!(seaborn도 마찬가지)

  • 대화형 파이썬 툴
    ▫ 노트필기 하듯이 코드 + 필기할 수 있는 툴 / 코드를 분할해서 실행이 가능!!




본론

저희는 다음과 같은 내용을 배웠는데요(3시간인 이유가 있습니다^^ 엉엉) 간단하게 요약해보도록 할게요!

  1. Numpy와 Pandas는 왜 중요한가?
  2. Numpy 넘파이
    • 넘파이 배열
    • 넘파이 배열 - ndarray와 관련된 함수들
  3. Pandas 판다스
    • 판다스의 주요 구성요소 - DataFrame, Series, Index
    • 기본 API들
    • DataFrame ←→ 리스트, 딕셔너리, 넘파이 ndarray
    • DataFrame 데이터 삭제
    • 데이터 셀렉션 및 필터링
    • 판다스 Aggregation 함수와 group by
    • 결손 데이터 처리
    • 판다스 apply, map


1️⃣ Numpy와 Pandas 왜 중요한가?!



제일 먼저 넘파이와 판다스가 많고 많은 라이브러리 중에 왜 중요한지 자세하게 알아보는 시간을 가졌습니다!

첫째 우리는 이미 기존에 있는 알고리즘을 이용해서 주어진 알고리즘이 결과를 잘 도출해낼 수 있도록 주어진 데이터를 적절하게 추출/가공/변환을 하는 것을 해야 합니다!
이때 데이터 처리를 할 때 대부분 넘파이와 판다스 라이브러리를 사용하기 때문에 중요한 것이겠지요?!

둘째 머신러닝 알고리즘의 모듈들이 모인 사이킷런이 넘파이 기반에서 작성됐기 때문에 넘파이를 잘 이해해야 합니다!
특히 뒤에서 알아보겠지만 넘파이 배열 꼭 중요한 부분이니까 기억해두는 것이 좋아요!


2️⃣ Numpy


  • 넘파이란? 넘파이는 파이썬으로 과학 계산을 할 때 필요한 패키지이자 라이브러리 이구요!! 다차원 배열을 위한 다양한 기능 선형대수 연산을 하는데 다양한 함수가 제공됩니다!


  • 넘파이 배열
    1) scikit-learn의 기본 데이터 구조!
    ▫ 사실 넘파이 라이브러리는 이 넘파이 배열을 사용하기 위해 가져왔다!! 라고 해도 과언이 아닐정도로 넘파이 배열은 정말 중요한 자료구조입니다!
    scikit-learn에서 알고리즘들이 넘파이 배열 형태의 데이터를 입력으로 받기 때문에 우리가 사용할 데이터들은 모두 넘파이 배열로 변환해줘야 합니다!

    cf) 파이썬은 자체적으로 배열 자료형을 제공하지 않기 때문에 배열을 사용하기 위해서는 넘파이를 사용


    2) ndarray

    ✏️ 개념 : 다차원(n-차원)의 배열(array) 자료구조 클래스 (단 배열의 원소 타입은 모두 같아야 한다)

    ✏️ 생성 : array(파이썬 list or ndarray)

    import numpy as np
    array1 = np.array([1,2,3]) #1차원 리스트 
    array2 = np.array([[1,2,3], [2,3,4]]) # 2차원 리스트 
    
    print("array1: \n", array1)
    print("array2: \n", array2)
    
    array1:
    [1 2 3]
    array2:
    [[1 2 3]
    [4 5 6]]
    


    ✏️ 형태(shpae) : ndarray.shape 속성

    array1 = np.array([1,2,3]) # 1차원 ndarray
    print('array1 type:',type(array1))
    print('array1 array 형태:',array1.shape) # 형태 알아보기 
    
    array2 = np.array([[1,2,3],
                    [2,3,4]]) # 2차원 
    print('array2 type:',type(array2))
    print('array2 array 형태:',array2.shape) # 형태알아보기 
    
    array3 = np.array([[1,2,3]]) #2차원 
    print('array3 type:',type(array3)) 
    print('array3 array 형태:',array3.shape) #형태 알아보기 
    
    array1 type: <class 'numpy.ndarray'>
    array1 array 형태: (3,)
    array2 type: <class 'numpy.ndarray'>
    array2 array 형태: (2, 3)
    array3 type: <class 'numpy.ndarray'>
    array3 array 형태: (1, 3)
    


    ✏️ 차원
    :ndarray.ndim 속성

      print('array1: {:0}차원, array2: {:1}차원, array3: {:2}차원'.format(array1.ndim,array2.ndim,array3.ndim))
      #차원 알아보기! 
    
      array1: 1차원, array2: 2차원, array3:  2차원
    


    ✏️ 타입(type)
    : ndarray.dtype 속성
    : ndarray 데이터 타입은 숫자, 문자열, bool 등등 모두 가능
    : 숫자형의 경우 int형(8bit, 16bit, 32bit) / unsigned int형(8bit, 16bit, 32bit) / float형(16bit, 32bit, 64bit, 128bit) / 이보다 더 큰 숫자도 가능 / 정밀도를 위해 complex 타입도 제공
    : ndarray내의 데이터 타입은 그 연산의 특성상 같은 데이터 타입만 가능!

        list1 = [1,2,3]
        print(type(list1)) #list 
        array1 = np.array(list1) 
    
        print(type(array1))# ndarray
        print(array1, array1.dtype) # 데이터 타입 알아보기 
    
        <class 'list'>
        <class 'numpy.ndarray'>
        [1 2 3] int32
    
         # 데이터 값의 타입이 다르다?!!? 
        list2 = [1, 2, 'test'] # 리스트는 가능 
        array2 = np.array(list2)
        print(array2, array2.dtype) 
        # ndarray는 안 됨! 이렇게 되면 정수형 값들이 크기가 더 큰 문자열 타입으로 변한다 
    
        list3 = [1, 2, 3.0] # 리스트는 가능
        array3 = np.array(list3)
        print(array3, array3.dtype) 
        # 정수형 값들이 모두 실수로 변함
    
        ['1' '2' 'test'] <U11
        [1. 2. 3.] float64
    


    ✏️ 타입(type) 변환
    : astype(변경을 원하는 타입)
    : 대용량 데이터를 다룰 때 메모리 절약을 위해 형변환을 특히 고려!

        array_int = np.array([1, 2, 3])
        array_float = array_int.astype('float64') # 64bit 실수형으로 변환해주세요! 
        print(array_float, array_float.dtype)
    
        array_int1= array_float.astype('int32') #32bit 정수형으로 변환!
        print(array_int1, array_int1.dtype)
    
        array_float1 = np.array([1.1, 2.1, 3.1])
        array_int2= array_float1.astype('int32') 
        print(array_int2, array_int2.dtype)
    


    ✏️ ndarray의 axis 축

    image

    ndarray의 shape는 행, 열, 높이 단위가 아닌 axis0, axis1, axis2와 같이 axis 단위로 부여!! (외우자 2차원 ndaary는 axis0 == 행 axis1 == 열 )



  • 넘파이 배열 - ndarray와 관련된 함수들

    1) ndarray 초기화 = arange, zeros, ones
    image
    ▫ zeros()와 ones()는 비슷합니다. 인자로 들어온 shape 형태로 0 또는 1.을 채워 ndarray를 반환해줍니다!
    ▫ 초기화 할 때 디폴트 데이터 타입은 float형으로 초기화 된 다는 것을 기억하세요!


    2) 차원과 크기를 변경 = reshape()

    image

      array1 = np.arange(10)
      print('array1:\n', array1)
    
      array2 = array1.reshape(2,5) # 이렇게 shpae() 변환! 
      print('array2:\n',array2)
    
      array3 = array1.reshape(5,2) #이렇게 shape() 변환
      print('array3:\n',array3)
    
        array1:
        [0 1 2 3 4 5 6 7 8 9]
        array2:
        [[0 1 2 3 4]
        [5 6 7 8 9]]
        array3:
        [[0 1]
        [2 3]
        [4 5]
        [6 7]
        [8 9]]
    


    2-1 reshape() 보충
    image
    ▫ 종종 reshape에서 인자로 -1이 들어가는 경우가 있습니다. -1의 의미는 해당 위치의 axis의 크기가 가변적이라는 뜻이에요!
    ▫ 즉 -1이 아닌 숫자에 해당하는 axis의 크기는 고정되지만 -1에 해당하는 axis의 크기는 고정 값에 맞추어 어떤 값이든 상관 없다는 뜻입니다!

        # 즉 열의 크기는 1로 고정하고 행의 크기는 자동으로 변환 해라! 
        x = np.arange(12) # 넘파이 배열 만들어주자~
        x = x.reshape(3,4)
        x.reshape(-1,2)
    
        array([[ 0,  1],
              [ 2,  3],
              [ 4,  5],
              [ 6,  7],
              [ 8,  9],
              [10, 11]])
    


    image
    ▫ (-1,1), (-1,)와 같은 형식으로 요구되는 경우가 많습니다 특히 머신러닝 API에서 넘파이 배열 인자를 1차원으로 반환해서 보내라! 혹은 2차원으로 반환해서 보내라! 와 같은 요구가 있을 때 유용하게 사용할 수 있습니다!
    ▫ 😈주의😈 (-1, -1) 쓰면 에러 발생합니다
    ▫ 😈주의😈 변환할 수 없는 shape구조를 입력하면 에러 발생합니다

        x.reshape(-1) # 1차원 배열을 반환! 
    
        array([ 0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11])
    
        x.reshape(1,-1) #1차원 배열처럼 보이지만 이는 (1,12)인 2차원 배열임!! 대괄호 수를 봐봐!
    
        array([[ 0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11]])
    


    3) ndarray의 데이터 세트 선택하기 - Indexing

    image
    이번에는 ndarray에서 원하는 데이터 셋을 필터링 해서 선택하는 인덱싱 방법에 대해서 알아보겠습니다!


    단일 값 추출
    그냥 배열에서 index로 값을 접근했던 것처럼 사용하시면 됩니다

    # 1에서 부터 9 까지의 1차원 ndarray 생성 
    array1 = np.arange(start=1, stop=10)
    print('array1:',array1)
    
    # index는 0 부터 시작하므로 array1[2]는 3번째 index 위치의 데이터 값을 의미
    value = array1[2] # 특정 값 추출
    print('value:',value) 
    print(type(value))
    
    array1: [1 2 3 4 5 6 7 8 9]
    value: 3
    <class 'numpy.int32'>
    


    슬라이싱
    :슬라이싱은 : 을 이용하여 연속된 값을 선택하는 방식입니다!
    :ndarray변수[시작인덱스:종료 인덱스]꼴
    :종료 인덱스-1까지만 인덱싱을 해줍니다
    :시작과 종료 인덱스에 아무것도 없으면 맨 처음, 맨 끝을 의미합니다

        array1d = np.arange(start=1, stop=10)
        array2d = array1d.reshape(3,3)
        print('array2d:\n',array2d)
    
        print('array2d[0:2, 0:2] \n', array2d[0:2, 0:2])
        print('array2d[1:3, 0:3] \n', array2d[1:3, 0:3])
        print('array2d[1:3, :] \n', array2d[1:3, :])
        print('array2d[:, :] \n', array2d[:, :])
        print('array2d[:2, 1:] \n', array2d[:2, 1:])
        print('array2d[:2, 0] \n', array2d[:2, 0])
    
        array2d:
          [[1 2 3]
          [4 5 6]
          [7 8 9]]
        array2d[0:2, 0:2] 
          [[1 2]
          [4 5]]
        array2d[1:3, 0:3] 
          [[4 5 6]
          [7 8 9]]
        array2d[1:3, :] 
          [[4 5 6]
          [7 8 9]]
        array2d[:, :] 
          [[1 2 3]
          [4 5 6]
          [7 8 9]]
        array2d[:2, 1:] 
          [[2 3]
          [5 6]]
        array2d[:2, 0] 
        [1 4]
    


    팬시 인덱싱 image
    :이 친구는 연속적이지 않습니다
    :리스트나 ndarray로 인덱스 집합을 지정해주면 해당 위치의 인덱스에 해당하는 값이 포함된 새로운 ndarray로 반환하게 됩니다

        array1d = np.arange(start=1, stop=10)
        array2d = array1d.reshape(3,3)
        print(array2d)
    
        array3 = array2d[[0,1], 2] # 행축의 0과1 인덱스 열축의 2 인덱스 가져와라
        print('array2d[[0,1], 2] => ',array3.tolist())
    
        array4 = array2d[[0,2], 0:2] #행으로 팬시 인덱싱 열축으로 슬라이싱 했음! 
        print('array2d[[0,2], 0:2] => ',array4.tolist())
    
        array5 = array2d[[0,1]] # 열축으로 아무것도 없으니까 모두 해당!  
        print('array2d[[0,1]] => ',array5.tolist())
    
        [[1 2 3]
        [4 5 6]
        [7 8 9]]
        array2d[[0,1], 2] =>  [3, 6]
        array2d[[0,2], 0:2] =>  [[1, 2], [7, 8]]
        array2d[[0,1]] =>  [[1, 2, 3], [4, 5, 6]]
    

    불린 인덱싱
    image
    불린 인덱싱은 가장 많이 쓰이는 인덱싱 방식입니다! 꼭 기억하세요!
    # 1차원 배열을 만들고
    array1d = np.arange(start=1, stop=10)
    
    # [ ] 안에 array1d > 5 Boolean indexing을 적용 
    print(array1d)
    array3 = array1d[array1d > 5]
    print('array1d > 5 불린 인덱싱 결과 값 :', array3)
    
    [1 2 3 4 5 6 7 8 9]
    array1d > 5 불린 인덱싱 결과 값 : [6 7 8 9]
    


    4) ndarray의 정렬과 선형대수 연산

    sort() image
    :np.sort()는 원본 행렬은 그대로 유지 되는데 원본 행렬의 정렬된 행렬을 새롭게 생성이 되어 반환됩니다!
    :ndarray.sort()를 하면 원본 행렬 자체가 정렬된 형태로 반환이 되는데 반환 값은 필요가 없습니다!
    :디폴트로 오름차순으로 정렬되고 내림차순으로 하고 싶은 분들은 [::-1]을 해주면 됩니다!

      org_array = np.array([ 3, 1, 9, 5]) 
      print('원본 배열:', org_array)
    
      # np.sort( )로 정렬 
      sort_array1 = np.sort(org_array)         
      print ('np.sort( ) 호출 후 반환된 정렬 배열:', sort_array1) 
      print('np.sort( ) 호출 후 원본 배열:', org_array) #원본 행렬 확인! 
    
      # ndarray.sort( )로 정렬
      sort_array2 = org_array.sort()
      org_array.sort()
      print('org_array.sort( ) 호출 후 반환된 배열:', sort_array2)
      print('org_array.sort( ) 호출 후 원본 배열:', org_array)
    
     원본 배열: [3 1 9 5]
     np.sort( ) 호출 후 반환된 정렬 배열: [1 3 5 9]
     np.sort( ) 호출 후 원본 배열: [3 1 9 5]
     org_array.sort( ) 호출 후 반환된 배열: None
     org_array.sort( ) 호출 후 원본 배열: [1 3 5 9]
    


    argsort()
    image
    :argsort()는 sort를 하긴 하는데 sort 가 되었을 때 해당 값의 원본 행렬의 인덱스 값들의 배열로서 반환해줍니다!

        org_array = np.array([ 3, 1, 9, 5]) 
        print(np.sort(org_array)) # 정렬된 값이 출력되는 반면
    
        sort_indices = np.argsort(org_array)
        print(type(sort_indices))
        print('배열 정렬 시 원본 배열의 인덱스:', sort_indices) # 정렬된 값의 원본 인덱스가 반환
    
     [1 3 5 9]
    <class 'numpy.ndarray'>
    배열 정렬 시 원본 배열의 인덱스: [1 0 3 2]
    


    np.dot(A,B)
    두 ndarray를 내적해줍니다!

        A = np.array([[1, 2, 3],
                [4, 5, 6]])
        B = np.array([[7, 8],
                [9, 10],
                [11, 12]])
    
        dot_product = np.dot(A, B)
        print('행렬 내적 결과:\n', dot_product)
    
      행렬 내적 결과:
        [[ 58  64]
        [139 154]]
    


    np.transpose(A)
    전치행렬을 반환해줍니다!

        A = np.array([[1, 2],
                [3, 4]])
        transpose_mat = np.transpose(A)
        print('A의 전치 행렬:\n', transpose_mat)
    
     A의 전치 행렬:
      [[1 3]
      [2 4]]
    


    더 자세한 코드는 Numpy를 참고하세요!



    🥕힘🥕들🥕어🥕요🥕!🥕




3️⃣ Pandas


  • 판다스란?
    image
    :판다스는 데이터 처리와 분석을 위해 존재하는 파이썬 라이브러리입니다!
    :판다스는 데이터프레임이라는 데이터 구조를 기반으로 만들어졌는데요 엑셀의 스프레드시트와 비슷한 테이블 형태라고 보시면 됩니다!
    :데이터 프레임을 수정하고 조작하는 다양한 기능을 제공해줍니다!
    :데이터를 수집하고 가공하고 다루는데 되게 편리한 API가 많이 제공되고 또 편리한 기능을 많이 제공합니다!!


  • 판다스의 주요 구성요소 - DataFrame, Series, Index imageDataFrame
    :DataFrame은 행과 열로 이루어진 2차원 데이터 셋입니다! 한마디로 테이블과 비슷하다고 보시면 됩니다!!
    :DataFrame은 기본적으로 numpy의 행은 ndarray로 이루어져있어요!! 심지어 컬럼명까지도요!!

    index
    :인덱스는 각 행을 고유하게 구별할 수 있는 키 값입니다! 쉽게 이야기해서 데이터 베이스의 pk 기본키같은 거다 라고 이해하시면 됩니다!
    :인덱스는 오직 식별용으로만 사용이 되고 연산에서 제외됩니다! 인덱스 값을 []로 접근해서 수정할 수 없습니다!!!
    :참고로 index는 객체 혹은 1차원 데이터 배열로 보시면 됩니다!!

    Series
    :1개의 컬럼값으로만 구성된 1차원 데이터 셋입니다!
    :시리즈가 여러개면 DataFrame이다 라고 이해하시면 됩니다!


  • 기본 API들
    코드가 너무 많은 관계로 판다스의 1번을 참고하세요!

    1) read_csv()
    :csv 파일을 편리하게 DataFrame으로 변환해줍니다!
    :read_csv() 의 sep 인자를 콤마(,)가 아닌 다른 분리자로 변경하여 다른 유형의 파일도 로드가 가능합니다.
    EX) sep 인자에 탭을 분리자로서 사용하겠다!!하면 pd.read_tsc(‘titanic_train.tsv’)로 바꾸면 됩니다!

    2) head()
    :DataFrame의 맨 앞 일부 데이터만 추출합니다
    :디폴트는 5개

    3) shape
    :DataFrame의 행(Row)와 열(Column) 크기를 가지고 있는 속성입니다.
    :걍 넘파이에서 나온 거랑 똑같다고 보면 됩니다!

    4) info()
    :DataFrame내의 컬럼명, 데이터 타입, Null건수, 데이터 건수 정보를 제공합니다.
    :데이터 타입도 있습니다! 참고로 object는 쉽게 말해서 문자열이라고 생각하면 됩니다.!
    :메모리 사용량이 나오는데 판다스의 데이터 프레임은 메모리에 올라가기 때문입니다!! 대용량 데이터를 사용할 때 주의해야 겠지요?!

    5) describe()
    :데이터값들의 평균,표준편차,4분위 분포도를 제공합니다. 숫자형 컬럼들에 대해서 해당 정보를 제공합니다

    6) value_counts()
    :한 컬럼에(시리즈에) 동일한 개별 데이터 값이 몇건이 있는지 정보를 제공합니다.
    :즉 개별 데이터값의 분포도를 제공합니다.
    :주의할 점은 value_counts()는 Series객체에서만 호출 될 수 있으므로 반드시 DataFrame을 단일 컬럼으로 입력하여 Series로 변환한 뒤 호출합니다.

    7) sort_values()
    :값을 정렬해줍니다!
    :인자 (by=정렬컬럼, ascending=True 또는 False로 오름차순/내림차순으로 정렬)
    :디폴트는 오름차순입니다!


  • DataFrame ←→ 리스트, 딕셔너리, 넘파이 ndarray

    image
    코드를 보고 싶으시면 판다스에서 2번을 보시면 됩니다!


  • DataFrame 데이터 삭제

    코드를 보고 싶으시면 판다스에서 3번을 보시면 됩니다!

    image
    axis
    :DataFrame의 로우를 삭제할 때는 axis=0, 컬럼을 삭제할 때는 axis=1로 설정합니다. (디폴트는 0임)
    :원본 DataFrame은 유지하고 드롭된 DataFrame을 새롭게 객체 변수로 받고 싶다면 inplace =False로 설정해줍니다(디폴트 값이 False임)
    EX) titanic_drop_df = titanic_df.drop(‘Age_0’, axis = 1, inplace=False)

    inplace=True
    :원본 DataFrame에 드롭된 결과를 적용할 경우에 적용합니다.
    EX) titanic_df.drop(‘Age_0’, axis = 1, inplace=True)

    ▫ 원본 DataFrame에서 드롭된 DataFrame을 다시 원본 DataFrame 객체 변수로 할당하면 원본 DataFrame에서 드롭된 결과를 적용할 경우와 같습니다.(단, 기존 원본 DataFrame 객체 변수는 메모리에서 추후 제거됨)
    EX) titanic_drop= titanic_df.drop(‘Age_0’, axis = 1, inplace=False) -> inplace=True와 같은 효과를 주는 것이죠!


  • 데이터 셀렉션 및 필터링

    코드를 보고 싶으시면 판다스에서 4번을 보시면 됩니다!

    image
    1번은 쉬우니까 넘어갈게요!!


    ▫ 명칭 및 위치 기반 인덱싱 image

    열과 행이 모두 5개인 데이터 프레임을 가져왔습니다!! 이때 빨간색 박스 부분은 명칭 기반 인덱스이고 노란색 숫자 부분은 위치 기반 인덱스입니다!
    위치 기반 인덱스는 절대 바뀌지 않습니다! 그래프 볼 때 원점이 바뀌지 않는 것처럼 항상 0부터 시작이 됩니다!
    그러나 Index는 명칭 기반 인덱스라서 데이터가 삭제되면 해당 값이 없어집니다!


    1) ✏️명칭 기반 인덱싱 - loc[]
    컬럼의 명칭을 기반으로 위치를 지정하는 방식, ‘컬럼 명’ 같이 명칭으로 열 위치를 지정하는 방식입니다!
    data = {'Name': ['Chulmin', 'Eunkyung','Jinwoong','Soobeom'],
        'Year': [2011, 2016, 2015, 2015],
        'Gender': ['Male', 'Female', 'Male', 'Male']
       }
    data_df = pd.DataFrame(data, index=['one','two','three','four'])
        
    data_df
    data_df.loc['one', 'Name']
    

    image

    'Chulmin'
    
    2) ✏️위치 기반 인덱싱 - iloc[]
    0을 출발점으로 하는 가로축, 세로축 좌표 기반의 행과 열 위치를 기반으로 데이터를 지정, 따라서 행, 열 위치값으로 정수를 입력해야 합니다!
    data_df
    data_df.iloc[0, 0] # 무조건 숫자가 들어간다!! 0번째 행 0번째 열 출력
    
    # 아래 코드는 오류를 발생합니다. 심지어 인덱스 객체를 넣어도 오류가 나옴!!
    data_df.iloc[0, 'Name']
    

    image

    'Chulmin'
    


    ▫ 불린 인덱싱
    헷갈리는 위치기반, 명칭기반 인덱싱을 사용할 필요없이 조건식을 [ ] 안에 기입하여 간편하게 필터링을 수행합니다.
    논리 연산자로 결합된 조건식도 불린 인덱싱 적용 됩니다!!

      titanic_df[titanic_df['Age'] > 60][['Name','Age']].head(3) #나이가 60세 이상
    

    image

  • 판다스 Aggregation 함수와 group by

    코드를 보고 싶으시면 판다스에서 잘 찾아 보시면 됩니다!(Hint 5번)

    ▫ Aggregation
    :sum(), max(), min(), count() 등의 함수는 DataFrame/Series에서 집합(aggregation) 연산을 수행합니다!
    :DataFrame의 경우 DataFrame에서 바로 aggregation을 호출할 경우 모든 컬럼에 해당 aggregation을 적용합니다!!


    ▫ groupby()
    :groupby() 메소드는 by 인자로 group by 하려는 컬럼명을 입력 받으면 DataFrameGroupBy 객체를 반환합니다!
    :이렇게 반환된 DataFrameGroupby 객체에 aggregation 함수를 수행하는데 편리합니다!

      titanic_groupby = titanic_df.groupby('Pclass').count() 
      # Pclass 부터 컬럼들이 나옴!! 
      # 이때 Pclass가 인덱스가 된다!! 특이하게도 group by로 하면 인덱스명이 Pclass로 부여가 된다!
      titanic_groupby
    

    image

      titanic_df[['Pclass','PassengerId', 'Survived']].groupby('Pclass').count()
      # 혹은 특정 컬럼들로 groupby 하겠어!! 
      # 이때 주의할 것은 Pclass가 반드시 존재해야 함!   
    

    image


  • 결손 데이터 처리

    코드를 보고 싶으시면 판다스에서 6번을 보시면 됩니다!

    ▫ isna()
    DataFrame의 isna() 메소드는 주어진 컬럼값들이 NaN인지 True/False 값을 반환합니다!(NaN이면 True)

      titanic_df.isna().head(3) # 즉 헤드의 3행인 애덜이 nan 값이니?!? -> 모든 컬럼에 대해서 확인 
    

    image


    ▫ fillna()
    미싱 데이터 값을 메소드에 주어진 인자값 즉, 변환할 인자값을 넣어주면 nan을 만날 때 이 값을 넣어줍니다!!
    머신러닝은 특히 입력값으로 null 즉, nan 값을 허용하지 않으니까!! 데이터 없는 것은 꼭!! 채워주시길 바랍니다!!

      titanic_df['Cabin'] = titanic_df['Cabin'].fillna('C000') 
      # 특정 컬럼에 대해서 null이 있으면 이 걸루 채워라!
      titanic_df.head(3)
    

    image


  • 판다스 apply, map

    코드를 보고 싶으시면 판다스에서 잘 찾아 보시면 됩니다!(Hint 마지막)

    ▫ apply
    image
    판다스는 applly 함수에 lamba 식을 결합해서 데이터 프레임이나 시리즈 별로 데이터를 가공할 수 있게 합니다!!
    apply 인자로 lamda 함수나 사용자 정의 함수를 넣어주셔도 됩니다!


    ▫ map
    image
    map도 apply처럼 함수 인자를 받아서 데이터를 처리할 수 있습니다!
    apply는 시리즈랑 데이터프레임 모두 다 가능하지만 map은 시리즈만 가능합니다!


결론

image 3시간을 버티고 잘 이해했나 퀴즈를 푸는 시간을 가졌습니다! 처음엔 모두 미소를 지으며 커리큘럼에 참여했지만 발표가 끝났을 때는 모두 지친 상태였답니다.. 허허허허 그럼에도 열심히 퀴즈를 풀었습니다!!


파이썬 과제를 풀어오는 것이 다음주 과제였습니다!! 다음주는 추석이지만 ML은 matplotlib와 seaborn을 공부해야 했습니다!!! 2주차 팀블로그도.. 곧 찾아옵니다 To be continued …



후기

image

  • 중요한 라이브러리들이라 배울 내용이 많아서 줄여도 줄여도 3시간 분량이 나오더랍니다… 첫 주차에 미친 분량임에도 끝까지 버텨준 ML 팀원에 박수!!👏👏 열심히 만들고 발표한 제 자신한테도 수고했다고 박수(와~~ 감사합니다!!!)👏👏
  • 머신러닝 알고리즘을 위해 데이터를 잘 다뤄야 한다고 많이 들었지만 어떻게 처리해줘야 할지 막막했었는데 이번 1주차 내용인 넘파이와 판다스 라이브러리를 알아가면서 자신감이 생겼습니다!! 넘파이와 판다스 라이브러리 내용은 정말 정말 중요하니까 잊어버리지 않기로 약속.. ^_~ (저는 더더욱 잊으면 안 됩니다. 몇 시간 동안 ppt 만들고 팀블로그 작성했는데 잊으면… NAVER(?)… R.E.M.E.M.B.E.R)