CafeM0ca

[Go] method, receiver (go 리시버) 본문

Programming/Go

[Go] method, receiver (go 리시버)

M0ca 2020. 12. 4. 12:36
반응형

tour.golang.org/methods/1

 

A Tour of Go

 

tour.golang.org

 

Go는 클래스가 없다. 하지만 특정 타입에 대한 메소드를 만들 수 있다.

이게 무슨 말 이냐 하면

Vertex와 Vertex3D 구조체가 있다.

Vertex는 Abs라는 메소드를 갖는다. 

 - func (v Vertex) Abs() float64

 

Vertex3D는 Abs라는 함수를 통해 연산이 가능하다.

main 함수에서 vertex구조체는 .을 통해 메소드를 호출하고 있고 vertex3D구조체는 Abs 함수를 통해 연산하고 있는 것을 볼 수 있다.

다른 언어랑 비교해봤을 때 이런 구조로 가져가면 장점이 무엇인가 생각해보면

내 생각엔 타 언어에서 클래스에 무수히 많은 함수들이 있고 생성된 인스턴스들이 절반도 안쓴다면 메모리 낭비가 될 것이다. 함수를 static을 갖게하면 모든 인스턴스들이 동일한 하나의 함수를 갖게 되니까 메모리 다이어트는 가능하겠지만.

 

하지만 Go에서는 타 언어의 인스턴스와 비교해보면 필요한 구조체만 해당 함수에 접근하면 되니까 메모리 다이어트가 필요 없게 되는 것 같다. 필요한 것만 쓰니까 좀 더 유연하달까? 어떤식으로 내부 동작하는 지는 나중에 더 공부하면서 알게 되겠지만..

 

아무튼!

메소드는 함수인데 특별한 인자가 필요하다. 그 인자는 func 키워드와 함수 이름 사이에 오는 타입이다.(굵은 글씨 부분)

 - func (v Vertex) Abs() float64

 

메소드는 함수라고 했으니 기능적으로 봤을 땐 함수랑 똑같이 동작한다.

꼭 구조체만 와야 하느냐? 그건 아니다. 일반 타입도 접근 가능하다.

대신 type 키워드를 통해 타입을 정의해줘야 한다.

메소드의 receiver는 pointer여도 된다.

v.add(1)을 통해 메소드를 호출하고 v 변수의 값을 1씩 증가시킨다.

 

pointer receiver를 사용하는데는 2가지가 있습니다.

1. 메소드가 receiver pointer의 값을 수정할 수 있다.

2. 메소드 호출에 따른 값의 복사를 방지하기 위해서 입니다. 구조체가 클 수록 효율이 좋습니다. 

2번의 경우 예제를 봅시다.

 

Scale과 Abs는 receiver 타입이 *Vertex다. 비록 Abs 메소드가 Receiver의 값을 수정하진 않지만 포인터로 되어있다.

 

일반적으로, 모든 메소드는 각각 value나 pointer receiver를 갖지만, 두 개를 섞어서 사용하진 않는다. 이 이유는 다음 게시물인 인터페이스에서 알아보자.

반응형

'Programming > Go' 카테고리의 다른 글

[Go] Type assertion, Type switch  (0) 2020.12.04
[Go] Interface  (0) 2020.12.04
[Go] A Tour of Go Exercise : Fibonacci closure 풀이  (0) 2020.12.03
[Go] A Tour of Go: Exercise Maps 풀이  (0) 2020.12.02
[Go] slice 탐구  (0) 2020.11.23
Comments