본문 바로가기
LG 헬로비전 DX DATA SCHOOL/Python

Python - 제어문과 함수 2

by 황밤 2023. 7. 10.
728x90
반응형

2023-07-10

 

2023.07.07 - [LG 헬로비전 DX DATA SCHOOL/Python] - Python - 제어문과 함수

 

Python - 제어문과 함수

2023-07-07 이전 Python 기초 내용을 보고싶으신 분은 아래를 클릭하세요! 2023.07.06 - [LG 헬로비전 DX DATA SCHOOL/Python] - Python 기초 Python 기초 2023-07-06 Python 파이썬은 프로그래밍언어 작성 후, 컴파일이 아

dxdata.tistory.com

 

앞의 제어문과 함수의 내용을 보실 분들은 윗 글을 눌러주세요.

 

오늘은 파이썬 함수에 대해 추가적으로 알아보도록 하겠습니다.

 

Python

일을 시킬 때 -> 함수가 좋다

저장을 할 때 -> 객체가 좋다

 

따라서, 처리와 일에는 파이썬/ 에코 시스템 제작은 자바가 좋다.

 

파이썬은 람다(메모리에 남겨놓지 않을 함수)를 한 줄로 밖에 작성이 불가하다. <-> 자바는 람다 사용에 유리함.

CI/CD는 무중단이 핵심이다.

 

map : 변환

filter : True/False 인 조건에 맞는 데이터


Function

1. 함수형 프로그래밍 관련 함수

1) map

  • 데이터를 변환하기 위한 함수
  • 이 함수에 하나의 매개변수를 갖고 하나의 데이터를 리턴하는 함수를 대입하면 리턴하는 데이터들을 모아서 리턴합니다.
  • 반복문을 이용해서 직접 변환하는 것도 속도가 훨씬 빠릅니다.


li = [i for i in range(10000)] # 0부터 9999까지의 숫자를 가지고 list 생성

temp = [] #반복문을 이용한 변환
for x in li :
    temp.append(x * x)

print(temp)

def f(x) :
    return x*x

#li의 모든 요소에 f 함수를 적용해서 변환한 결과를 temp에 대입
temp = list(map(f, li)) # map을 이용한 변환
print(temp)

#람다 사용
#함수의 내용이 한 줄 이므로 람다로 처리
temp = list(map(lambda x : x*x , li))

 

 

2) filter

  • 컬렉션과 리턴 타입이 bool 인 함수를 매개변수로 받아서 컬렉션의 모든 데이터를 함수의 매개변수로 대입해서 리턴되는 결과가 True인 경우만 iterator 인스턴스로 리턴하는 함수
  • 대입되는 함수는 하나의 매개변수를 받아서 bool 리턴하는 함수 이어야 함
ar = ["김구", "김좌진", "안중근", "윤봉길", None]

print(None in ar)

#이름이 3자 이상인 데이터만 출력
#None 확인 및 제거
def f1(x) :
return x != None

ar = list(filter(f1, ar))
print(ar)
def f2(x) :
return len(x) >= 3

result = list(filter(f2, ar))
print(result)
#한줄 함수를 lambda로 변경
ar = list(filter(lambda x : x != None , ar))
print(ar)

result = list(filter(lambda x : len(x) >= 3, ar))
print(result)

result = list(filter(lambda x : x[0] >= "" and x[0]< "" , ar))
print(result)

 

3) reduce

  • 데이터의 모임을 가지고 연산을 수행해서 하나의 결과를 만들어내는 작업
  • 파이썬에서는 예전에는 기본함수였으나, 지금은 functools 내 함수로 변경이 됨. -> 매개변수가 2개이고 하나의 결과를 만들어내는 함수를 대입해야함.

 

4) zip(내장함수)

  • 여러 개의 데이터 모임을 받아서 하나의 데이터로 묶어주는 함수
  • 데이터는 tuple로 묶어줍니다.
  • 데이터의 모임에 데이터 개수가 일치해야 합니다.
key = ["국민학교", "중학교", "고등학교"]
value = ["만재국민학교", "광주서중", "명덕고등학교"]

print(list(zip(key, value)))
print(dict(zip(key, value)))

 

5) High Order Function(고위 함수)

  • 함수를 매개변수로 받거나 함수를 리턴하는 함수

6) 중첩 함수

  • 파이썬에서는 함수 내부에 함수를 만들 수 있습니다.
  • 파이썬의 함수는 기본적으로 함수 외부에 직접 접근하는 것은 불가능. => 함수 내부에서 변수를 만들면 무조건 지역 변수로 생성.
  • 내부에 만든 함수는 자신을 포함한 함수의 데이터에 접근하는 것이 가능합니다.
  • 외부 함수는 내부 함수의 데이터에 접근하는 것이 안됨
  • 내부 함수는 함수 외부에서 직접 호출이 안됨
  • 함수 내부에서 데이터를 읽기만 하는 경우는 자신에게서 생성안되어 있는 경우에는 외부에서 변수를 찾아서 읽기를 수행하는데, 함수 내부에서 데이터를 생성(대입하는 연산자를 사용)하는 경우에는 내부의 데이터를 사용하는데 이 경우에는 반드시 먼저 생성하는 문장이 있어야 합니다.
  • 함수를 만들어서 호출을 하면 먼저 함수 내부를 확인해서 함수 내부에 대입문이 있으면 대입문에 사용된 이름들을 로컬 변수로 간주를 하고 함수를 호출할 때 변수의 이름만 사용하면 로컬에 있는 변수를 호출하는 문장으로 해석하고 로컬 변수가 아닌 변수 이름을 사용하면 함수 외부에서 만든 것으로 간주합니다.

Global : 모든 곳에서 사용가능한 데이터 블럭 외부에서 생성

Member : Class 내부에 선언해서 Instance가 사용

Local : 함수 내부에서 함수 내부에서만 사용이 가능한 

 

def outer() :
    outer_data = "외부 함수의 데이터"

    def inner () :
        inner_data = "내부 함수의 데이터"
        #local.outer_data inner에 쓸려면 있어야 할 위치
        print(outer_data) #local.outer_data
        #outer_data = "내부에서 외부 함수 변경" #local variable 'outer_data' referenced before assignment
    print(outer_data) #local.outer_data

    inner()
print(outer_data)

 

 

7) nonlocal 과 global

  • 함수 내부에 nonlocal 이나 global 이라는 키워드와 함께 변수 이름을 기재하면 함수 내부에서 변수 이름을 이용해서 지역 변수를 만들 수 없게 되고 nonlocal 을 기재한 경우는 자신의 외부에서부터 데이터를 찾아가게 되고 global을 붙이면 최상위 레벨의 데이터를 사용합니다.
def outer() :
    outer_data = "외부 함수의 데이터"

    def inner () :
        nonlocal outer_data #함수 완전 밖에 변수가 존재할 시, global로 바꾸면 됨
        print(outer_data) #nonlocal.outer_data

        print(outer_data) #nonlocal.outer_data

    inner()
    print(outer_data)

 outer()
a = outer()

 

  • 동일한 이름의 변수가 최상위 레벨에 존재하는 경우는 nonlocal이 아니고 global로 만들어야 한다.
  • 동일한 이름의 변수를 여러 번 사용하면 이러한 문제가 발생할 수 있기 때문에 변수의 이름을 중첩되지 않게 잘 만들어야 하는데 예전에는 이 문제를 유효 범위를 표시해서 해결했는데 로컬 변수의 이름 앞에는 _, 멤버 변수의 이름 앞에는 m_, 전역 변수의 앞에는 g_를 붙이기도 했다.

 

8) closure

함수 내부에서 만든 함수를 리턴해서 함수 외부에서 함수 내부의 데이터를 변경할 목적으로 사용

  • 함수 안에서 만든 데이터는 함수를 호출하고 나면 소멸됨.
  • 함수 내부와 외부에서 데이터를 공유하고자 하는 경우 전역 변수를 만들어서 사용할 수 있는데 구조적 프로그래밍이나 객체 지향 프로그래밍에서는 전역 변수를 만드는 것을 권장하지 않습니다.
  • 이런 경우 closure를 이용해서 사용하기를 권장합니다.
def outer() :
    amore = "아모르파티"
    #자신을 감싸고 있는 함수의 데이터를 수정하는 함수
    def inner() :
        nonlocal amore
        amore = amore + "아모르"
        print(amore)
        #함수 내부의 데이터를 수정하는 함수를 리턴하는 함수를 closure 라고 한다.
    return inner

closure = outer() #함수를 호출해, 리턴하는 함수를 변수에 저장
closure()

 

Business Logic
: 실제 업무

Common Concern(공통 관심 사항)
: 업무와 직접적인 관련이 없는 (로그인, 로깅 등)

위 두개를 분리해서 프로그래밍을 하고, 추후에 결합하자!

2. Decorator

  • 로직을 수행하기 전이나 수행한 후에 해야 할 일을 별도의 메서드로 만들어두고 @함수이름으로 대신하도록 하는 것
  • 생성 작업이 복잡하거나 알 필요가 없는 경우 또는 business logic(업무 로직)과 common concern(공통 관심 사항-로깅이나 벤치마크를 위한 테스트 코드 등)을 분리하고자 하는 경우 사용한다.
def amore(func) :
    func()
    print("로깅")
@amore
def businessLogic():
    print("비지니스 로직")

businessLogic()
  • decorator를 만들 때 대부분의 경우는 함수를 리턴해서 리턴한 함수가 수행되도록 합니다.
  • decorator에 전달된 매개변수를 이용해서 함수의 이름이나 전달된 인수 그리고 리턴 값도 확인할 수 있습니다.
  • 함수를 호출할 때 마다 실행에 걸린 시간, 인수, 리턴 값을 출력하는 decorator를 생성
import time

def clock(func) :
#decorator 가 적용된 함수가 호출되면 수행될 실제 함수

    def clocked(*args) :
#업무 로직 함수를 호출

        start = time.time() #현재 시간을 기록

        result = func(*args)

        end = time.time()
        elapsed = end - start #함수의 수행시간
        print("수행시간 :", elapsed)

#매개변수 확인
        print("매개변수 :", args)

#리턴값
        print("리턴값 :", result)

        return result
return clocked

@clock
def myfunc(n) :
    a = "dx "
    b = "data \n"

    result = (a+b) * n
    return result

myfunc(10)

%%decorator는 매우 중요%%

 

  • 표준 라이브러리에서 제공하는 데코레이터
  • functools 패키지에서 제공하는 lru_cache() 라는 데코레이터를 이용하면 중복된 함수 호출이 있는 경우 함수를 호출하지 않고 결과를 재사용할 수 있다.
  • lru는 무한정 캐싱되는 현상을 방지하기 위해서 오랫동안 사용하지 않은 데이터를 캐시에서 제거하는 알고리즘

 

3. OOP(Object Oriented Programming - 객체 지향 프로그래밍)

 

개요

1) 3대 특징

  • Encapsulation(캡슐화)

불필요한 정보는 숨기고 중요한 정보 만을 표현해서 프로그램을 간단하게 만드는 것(인터페이스를 간단하게 만드는 것)

  • Inheritance(상속)

하위 클래스가 상위 클래스의 모든 요소를 물려받는 것

  • Polumorphism(다형성)

동일한 메시지에 대하여 다르게 반응하는 성질

 

 

2) 용어

 

  • Object(객체) : 프로그램에 사용되는 모든 것

 

  • Class : 사용자 정의 자료형

동일한 목적을 달성하기 위해 모인 속성(데이터)과 메서드(기능 - 함수)의 집합

정적(static) : 한 번 만들면 변경되지 않는

 

  • Instance : Class를 기반으로 메모리 할당을 받은 객체

동적(Dynamic): 변경 가능한 

 

  • 정적 바인딩과 동적 바인딩

정적 바인딩은 실행 전에 결정되는 것 - 변수를 만들 때 자료형을 명시적으로 작성하거나 암묵적으로 결정해두고 사용하기 때문에 실행 중에 변수에 다른 종류의 데이터를 삽입할 수 없음.

 

동적 바인딩은 실행 중에 결정 가능한 것 - 참조형 데이터만 존재하고 변수는 데이터의 참조를 저장하기 때문에 실행 중에도 다른 종류의 데이터를 대입할 수 있음.

 

  • 속성(attribute) : Instance를 구성하는 데이터
  • method : Class 안에 만들어진 기능(함수)
  • property : 속성처럼 사용하는데 실제로는 method를 호출하는 것
  • record 나 structure(구조체) : 하나의 행을 의미, Instance를 구성하는 속성의 집합
  • python의 모든 데이터는 기본적으로 instance
  • Information Hiding(정보 은닉) : 불필요한 부분을 숨기는 것

3) Class 와 Instance

 

1))클래스 생성

 

class 클래스 이름 :

        초기화 메서드 생성

 

        메서드 생성

 

 

2))인스턴스 생성

  • 인스턴스 이름 = 초기화 메서드(매개변수) -> 초기화 메서드의 이름은 클래스 이름
  • 인스턴스를 생성하는 메서드를 호출하면 인스턴스를 생성하고 그 참조를 리턴

 

3))인스턴스나 클래스를 이용한 멤버 호출

  • 인스턴스나 클래스.속성
  • 인스턴스나 클래스.메서드(매개변수)

 

4)) Method

  • 인스턴스가 있어야 만 호출되는 메서드와 인스턴스가 없어도 호출되는 메서드(static, class)로 구분
  • 인스턴스가 없어야 하는 메서드 생성

def 메서드 이름(인스턴스를 참조를 저장할 매개변수[, 매개변수 나열]) :

         내용

 

관례상 인스턴스 참조를 저장할 매개변수의 이름은 self

  • 인스턴스가 있어야 하는 메서드 호출

클래스 이름.메서드 이름(인스턴스, 매개변수) : Unbound 호출

인스턴스.메서드 이름(매개변수) : Bound 호출

클래스 내부의 다른 메서드에서 호출 : self.메서드이름(매개변수)

 

 

5) 인스턴스의 속성 만들기

 

  • 파이썬에서 인스턴스의 속성을 만들고자 하는 경우에는 인스턴스가 있어야 호출되는 메서드 안에서 self.속성명으로 데이터를 대입하면 만들어 집니다.
  • 클래스 외부에서 인스턴스.속성이름 = 데이터 코드를 작성하면 속성이 존재하면 속성의 값을 변경하는 것이고 속성이 존재하지 않으면, 속성이 생성된다.

 

6) 클래스 속성 만들기

  • class 내부 그리고 method 외부에 변수를 생성해서 데이터를 대입하면 class 속성이 됩니다.
  • class 의 속성은 클래스와 인스턴스 모두 접근이 가능하다.
  • 인스턴스를 이용해서 접근할 때 그 속성이 인스턴스 내부에 없으면 class 속성을 호출하지만 인스턴스 내부에 존재하면 인스턴스의 속성을 호출합니다.
  • 대입문을 이용하면 인스턴스의 속성을 생성해서 사용한다.
  • 클래스 속성은 인스턴스를 이용해서 접근하는 것을 권장하지 않는다.

7) is 연산자

  • python의 변수는 데이터를 저장하고 그 데이터의 id를 저장하는 개념
  • == 연산자는 목적이 id를 비교하는 것이 아닙니다. 파이썬에서는 == 연산자는 내부에 만든 __eq__ 메서드를 호출해서 그 결과를 리턴하는 연산자입니다.
  • id를 비교하는 연산자는 is 연산자이며, 오버로딩이 안되기 때문에 명확하게 id를 비교한다고 할 수 있습니다.
class Student:
    class_data = "클래스의 속성"

#인스턴스 생성해서 대입
stu1 = Student()
#인스턴스 생성해서 대입
stu2 = Student()
#stu1 의 데이터를 대입 : stu1 이 참조하고 있는 데이터의 참조를 stu3가 참조합니다.
stu3 = stu1

print(stu1 == stu2) #내부의 데이터가 같은지 확인
print(stu1 is stu2) #id가 같은지 확인
print(stu1 is stu3)# true
print(stu1 == stu3)# true

 

8) Accessor - 접근자 메서드

  • 객체 지향 언어에서는 인스턴스를 가지고 속성에 직접 접근하는 것을 권장하지 않는다.
  • 속성에 접근하는 메서드를 이용해서 속성의 값을 가져다가 사용하고 수정하도록 한다.

속성의 값을 리턴하는 메서드를 getter 라고 하며, 속성의 값을 수정하는 메서드를 setter 라고 한다.

 

  • getter

이름은 get속성이름으로 하고 매개변수는 일반적으로 없고 속성을 리턴하기만 합니다.

속성의 자료형이 bool 인 경우 get 대신에 is를 붙인다.

속성의 이름의 첫글자는 대문자로 표기하는데 파이썬에서는 대문자 대신에 _를 사용하는 경우가 있다.

 

  • setter

이름은 set 속성이름으로 하고 매개변수는 속성과 동일한 자료형의 데이터 1개로 생성

내용은 매개변수로 받은 데이터를 속성에 대입합니다.

 

 

  • 속성의 자료형이 Sequence(list) 인 경우

인덱스를 받아서 인덱스 번째 데이터를 리턴하는 getter를 추가로 생성하고 인덱스 와 데이터 1개를 받아서 인덱스 번째 데이터를 수정하는 setter를 생성하기도 한다.

 


class Student :

def getName(self): #매개변수 없음
    return self.name

def setName(self, name): #자료형과 동일한 매개변수 1
    self.name = name

def getScore(self):
    return self.score

def setScore(self, score):
    self.score = score

#인스턴스 생성
stu1 = Student()

#setter를 이용한 속성 생성과 설정
stu1.setName("애니")
stu1.setScore(98)

#getter를 이용한 속성 사용
print(stu1.getName())
print(stu1.getScore())

#최근 등장 IDE는 대부분 getter setter를 만드는 유틸을 제공합니다

수고하셨습니다!

 

 

 

 

ps) 인스턴스란, 어떤 클래스에 속하는 각 객체들을 지칭하는 말이다. (객체 지향 프로그래밍)

반응형
LIST

'LG 헬로비전 DX DATA SCHOOL > Python' 카테고리의 다른 글

Python 예외처리 / File handling  (0) 2023.07.14
파이썬 Data Type 및 처리  (0) 2023.07.11
객체 지향 프로그래밍 (OOP)  (0) 2023.07.11
Python - 제어문과 함수  (0) 2023.07.07
Python 기초  (0) 2023.07.06