SK shieldus Rookies 16기 (인프라 활용을 위한 파이썬 #03)

만두다섯개·2023년 10월 26일
0

SK 루키즈 16기

목록 보기
3/52

주요 정보

교육 과정명 : 클라우드기반 스마트융합보안 과정 16기
교육 회차 정보 : '23. 10. 26. 인프라 활용을 위한 파이썬 과정 #3

참고 정보

  • 일차 : 2일차 복습(tictacto 프로그램 ver5까지) + 파일 입출력 및 클래스
  • 클래스 내 함수, 메소드와 객체 혼용( => 객체 참조하는 것이 메소드)

보완할 점

  • 3일차 파이썬 교육 정리 : 파일 입출력

무엇을 깨달았나

  • 파이썬에서의 클래스 기초적인 사용방법 및 상속개념
  • 파이썬에서의 기초적인 파일 입출력(shutil, pickle)

첨언

  • 보안 이슈, 새로운 툴 항상 체크 (log4J 언급)
  • 보안 VS 개발자 입장 차이
  • 코드 가독성(한줄이 아닌 아래로)
  • 강의자료 3일차: 클래스 부분 (print 메소드 2버전 호환 x)

파이썬에서의 클래스

  • 파이썬 함수위주 사용하지만 객체지향 가능
  • 객체 내부 데이터를 메서드로 수정 가능(this, self 키워드: 차이는 있지만 비슷함)
  • 객체는 클래스의 인스턴스다
  • 클래스 선언 후 pass 입력 및 추후 추가 가능 (pass 조차 없으면 안됌)
  1. 클래스 작성 방법 : 클래스이름은 대문자
class NewClass:
	__init__(self, name):  # __init__() : 생성자 : 객체 생성시 자동 실행. 생성시 필요 코드 포함
    #self: 생성자 파라미터로 생성된 객체의 멤버에 접근시 사용한다
    self.name = name
  1. 클래스 실습(#1)
class Person:
    name = '바세린맛소주' #call by value, 리스트 생성시 call by reference 된다.
    gender = 'male'
    address = 'yeosu'

    def set_name(self, name):  # 클래스의 메소드, 매개변수 : self, name
        self.name = name  #self 객체 멤버 접근 목적 사용하는 매개변수
        
    def print(self):
        print('my name is {0}'.format(self.name))

    @staticmethod # 정적 메서드
    def set_name2(name):
        print(f'따로 논다{name}')
        
person = Person() #클래스로부터 객체를 생성한다
person.set_name('david') #클래스의 메소드를 사용해 name을 가진다
person.print() # 클래스의 print 메소드를 사용해 객체의 name 을 출력한다

클래스실습(#1) - 출력

my name is david
  1. 클래스 실습(#2)
class Animal:
    def __init__(self) :  #객체 생성시 자동으로 실행된다.
        self.name = 'cat'
        self.age = '14'
    def set_name(self, name):
        self.name = name
    def print(self):
        print(self.name)
     
animal = Animal()
animal.set_name('깜냥이')
animal.print()

second_animal = Animal()
second_animal.__init__()
second_animal.print()

클래스 실습(#2) - 출력

깜냥이
cat
  1. 클래스 실습(#3)
class Animal:
    __NAME = 'private'  # 클래스 내부에서만 접근 가능한 비공개 속성 부여 변수
    def __init__(self, name='animal', age=12, is_hungry=False) :  #객체 생성시 자동 실행
        self.name = name
        self.age = age
        self.is_hungry = is_hungry
        self.__print() # 객체를 생성하면, __init__() 메소드 자동 실행으로
        #self.__print() 실행되어, 클래스 내부에서 정의된 __print() 메소드 실행된다. \
        #따라서 객체 생성마다 private  출력됨

    def __print(self):
        print(self.__NAME)    
# hotdog = Animal()
# hotdog.__print() # 속성이 없어서 출력 안됨. 단 hotdog 객체 생성시에는 __print 메소드 실행된다.

zebra = Animal()
print(zebra.name, zebra.age, zebra.is_hungry )
zebra.__print()  # 속성을 부여한 객체도 __print 메소드를 사용하지 못한다. 해당 메소드는 객체 생성시에만 실행 가능
zebra.__init__() # private 출력된다. 이는 __init__() 메소드를 실행 가능의미
  • 비공개 속성이 부여된 메소드를 클래스 외부에서 호출 불가능, 단, 클래스 호출 가능한 함수로 클래스 내부에서 호출하는 것은 가능하다. -> zebra.init() 함수로 private 출력한 것.
    클래스 실습(#3) -출력
---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
d:\python_study\pythonProject001\day3\class_ex.ipynb 셀 6 line 3
      1 zebra = Animal()
      2 print(zebra.name, zebra.age, zebra.is_hungry )
----> 3 zebra.__print()
      5 # hotdog = Animal()
      6 # hotdog.__print() # 속성이 없어서 출력 안됨. 단 hotdog 객체 생성시에는 __print 메소드 실행된다.

AttributeError: 'Animal' object has no attribute '__print'
  1. 클래스 실습(#4)
class ShoppingCart: #쇼핑카트 클래스 생성
    # items_in_cart = {} # 카트(물건:값 - 키:값) 딕셔너리 생성. 해당 위치 딕셔너리 생성시, 해당 클래스를 참조하는 모든 객체가 동일한 주소의 딕셔너리를 공유하게 된다.    # 웹 페이지는 접속마다 세션이 생성되어 클래스 공유가 안 된다. 
    def __init__(self, customer_name):  # 초기함수: 고객 이름 
        #self 변수는 객체 데이터로 메서드 사용목적으로 사용
        self.__items_in_cart = {}
        print(customer_name + " 고객님의 카트 id는 다음과 같습니다. " + str(id(self.__items_in_cart)))
        self.customer_name = customer_name
    def add_item(self, prodcut, price): # 상품 추가 : 상품이름, 가격
        if not prodcut in self.__items_in_cart: # 아이템 카트에 product 가 없으면, prodcut를 key, price value 로 카트(딕셔너리)에 추가
            self.__items_in_cart[prodcut] = price
            print(prodcut + ' 이 추가되었습니다')
        else:
            print(prodcut + '이미 카트에 담겨있습니다')
    def remove_item(self, product): 
        if product in self.__items_in_cart:
            del self.__items_in_cart[product]
            print(product + " 이 삭제되었습니다")
        else:
            print(product + " 이 카트에 없습니다")
    def print_items(self):  # 카트에 담긴 아이템 목록 출력
        print(self.__items_in_cart)

a_cart = ShoppingCart('a') #a 라는 고객의 쇼핑카트 생성, 객체명은 a_cart
b_cart = ShoppingCart('b')

a_cart.add_item('간장', 10000)  
a_cart.add_item('감자', 222)  
b_cart.add_item('호떡', 300)
b_cart.add_item('홍박사', 999)

a_cart.print_items()
b_cart.print_items()

a_cart.remove_item('간장')
b_cart.remove_item('홍박사')

a_cart.print_items()
b_cart.print_items()
  • 카트(딕셔너리) 선언 위치에 따른 딕셔너리 ID
  1. 클래스 바로 아래 : A, B 객체가 클래스 참조시 동일한 주소의 딕셔너리 사용
  2. init 함수 아래(표기상 언더바 표기안됌) : A, B 객체가 클래스 참조시 다른 주소(다른 딕셔너리) 사용
    클래스 실습(#4) - 출력
a 고객님의 카트 id는 다음과 같습니다. 2559935417024
b 고객님의 카트 id는 다음과 같습니다. 2559929947264
간장 이 추가되었습니다
감자 이 추가되었습니다
호떡 이 추가되었습니다
홍박사 이 추가되었습니다
{'간장': 10000, '감자': 222}
{'호떡': 300, '홍박사': 999}
간장 이 삭제되었습니다
홍박사 이 삭제되었습니다
{'감자': 222}
{'호떡': 300}
  1. 클래스 실습(#5) : 상속 실습
  • A클래스를 상속한 B클래스는 init 그대로 가져온다. -> 선언 생략 가능
class Empolyee: 
    def __init__(self,name): # Empolyee 클래스는 이름을 초기변수로 가진다
        self.name = name
    def greet(self, other:object):  # greet 메소드 선언 : other 변수로 인사한다 (:object 생략가능)
        print("직원이 말합니다.")
        print("인사드립니다! %s 님!!!" % other.name)

class CEO(Empolyee): # CEO 클래스는 Empolyee 클래스를 상속한다
    def greet(self, other):  
        print("CEO가 말합니다.")
        print("반가워용 %s 씨!" % other.name)

class CAO(Empolyee):
    pass
# def greet(self, other):  
# print("CAO가 말합니다.")
# print("넵넵넵넵 반가워요~ %s 님~~~" % other.name)      

# emp = Empolyee('코코')
# ceo = CEO('킹갓체어맨아반떼소유주')
# cao = CAO('지상최고의경영품질관리신')
# emp.greet(ceo)
# ceo.greet(emp)
# cao.greet(cao)

emp = Empolyee('김인턴아직신입도아님')
ceo = CEO('회장도배달비아깝다')
cao = CAO('CAO라는자리있는거맞지?')

emp.greet(ceo)
emp.greet(cao)

cao.greet(emp)  # greet 메소드 사용가능하다. 단, Empolyee 클래스의 greet 메소드를 가져와 사용한다.

클래스 실습(#5) - 출력

직원이 말합니다.
인사드립니다! 회장도배달비아깝다 님!!!
직원이 말합니다.
인사드립니다! CAO라는자리있는거맞지? 님!!!
직원이 말합니다.
인사드립니다! 김인턴아직신입도아님 님!!!

파일 - 쓰기, 읽기

  • 파일 사용의 순서 : 파일 열기, 파일 사용(쓰기, 읽기), 파일 닫기 => 메모리 누수 방지

파일 쓰기

  • os 모듈필요하다. open()메소드 사용한다.
  • 파일의 이름, 파일사용 권한 명시한다.

파일 읽기

  • open() 메소드와 r 권한으로 파일을 연다
  • read() 메소드는 파일 전체를 읽는다
  • readline() 메소드는 파일에서 한 줄만 읽는다
  • readline()메소드는 리스트형식으로 불러오기 때문에 반복문 사용시 한 글자씩 출력
  • while을 사용해서 파일을 읽을 때에는, [if not line: break]처럼 반복문에서 탈출해야 한다(메모리 누수 방지)
  • 위에서 언급한 line은 readline의 인자로 사용한다.

파일 정리하기 – shutil, zipfile

shutil 이용한 파일과 디렉터리 복사, 이동

  • shutil 모듈이 필요하다.
  • shutil.copy(‘A’,‘B’) : A파일을 B경로로 복사
  • shutil.copytree(‘A’,‘B’) : A경로의 파일을 B경로로 복사
  • shutil.move(‘A’,‘B’) : A파일을 B경로로 이동
 - 경로 명시할때는 [\]를  [\\]로 두 번 사용해야 한다.

pickle 이용한 파일과 디렉터리 복사, 이동

  • 모델 저장 시 사용
  • 저장 및 불러오기 바이너리파일 형식으로 가져온다
  • .dat 파일을 쓰고(wb), 읽어온다(rb)

profile
磨斧爲針

0개의 댓글