개발바닥

인터페이스 (interface) 본문

GO 언어

인터페이스 (interface)

라이언 2022. 3. 6. 22:28
반응형

Go 인터페이스란?

이기종간 기능을 약속하여 서로 다른 기기일지라도 오직 기능적인 관점에서 일관성을 유지하기 위해 사용한다.

Go에서 구조체는 필드들의 집합체라면, 인터페이스는 메서드들의 집합체이다.

인터페이스는 타입이 구현해야 하는 메서드 원형들을 정의한다.

인터페이스의 이름은 보통 변수에 ~er이 붙는다.

특정 타입이 인터페이스에서 정의된 메소드를 구현했다면, 해당 타입은 인터페이스를 구현했다고 본다.

 

인터페이스 선언

type 인터페이스명 interface{
   ...
   메소드
   ...
  }

 

인터페이스를 왜 쓰는가?

타입 확장에 유연하게 대응하기 위함

Go 언어에서는 매개변수와 반환이 다르더라도 이름이 같은 메서드는 있을 수 없다. 

 

이러한 문제점을 해결하기 위해서 메소드명을 다르게 해서 해결할 수 있지만,

좋은 선택은 아니다. 인터페이스를 통해서 이러한 문제점을 해결할 수 있다.

 

package main

import "fmt"

type Bank interface {
	WithDraw(price int) bool
	Deposit(price int) bool
}

type KakaoBank struct {
	Balance int
}

type KBBank struct {
	Balance int
}

func (kakao KakaoBank) WithDraw(price int) bool {
	if kakao.Balance >= price {
		kakao.Balance -= price
		return true
	}
	return false
}
func (kakao KakaoBank) Deposit(price int) bool {
	fmt.Println("카뱅 기존 잔고 : ", kakao.Balance)
	kakao.Balance += price
	fmt.Println("카뱅 현재 잔고 : ", kakao.Balance)
	return true
}

func (kb KBBank) WithDraw(price int) bool {
	if kb.Balance >= price {
		kb.Balance -= price
		return true
	}
	return false
}

// 입금하면 2배 이벤트
func (kb KBBank) Deposit(price int) bool {
	fmt.Println("기존 잔고 : ", kb.Balance)
	kb.Balance += (price * 2)
	fmt.Println("현재 이벤트로 인해서 2배로 입금 완료! 현재 잔고 : ", kb.Balance)

	return true
}

func main() {
	kakao := KakaoBank{10000}
	kb := KBBank{5000}

	kakao.Deposit(2000)
	kb.Deposit(10000)

}

 

결과 화면

카뱅 기존 잔고 :  10000
카뱅 현재 잔고 :  12000
기존 잔고 :  5000
현재 이벤트로 인해서 2배로 입금 완료! 현재 잔고 :  25000

 

위 코드 처럼 공통으로 사용되는 WithDraw, Deposit 공통 메서드를 인터페이스에 선언한다.

카카오뱅크, kb뱅크 타입을 선언 후 메소드 원형들을 구현해서 사용하면 된다.

이렇게 사용하면 관리가 쉽고 가시성이 높아진다. 

 

인터페이스 기능 더 알아보기

1. embedded 인터페이스

구조체에서 다른 구조체를 포함된 필드로 가질 수 있듯이 인터페이스도 다른 인터페이스를 포함할 수 있다.

 

2. empty 인터페이스

interface{}는 메서드를 가지고 있지 않은 빈 인터페이스이다. 가지고 있어야 할 메서드가 하나도 없기 때문에 모든 타입이 빈 인터페이스로 쓰일 수 있다. ( 빈 인터페이스는 어떤 값이든 받을 수 있는 함수, 메서드, 변수값을 만들 때 사용한다.)

 

package main

import (
	"fmt"
	"strconv"
)

// 코드에 보시다시피 interface{} 로 받은 매개변수를 사용하기 위해서는 타입을 변환을 해주어야 된다.
func TypeCheck(arg interface{}) string {
	switch arg.(type) {
	case int:
		fmt.Println("int 형 입니다.", arg)
		i := arg.(int)         // int 형변환
		return strconv.Itoa(i) 
	case float32:
		fmt.Println("float32 형 입니다.", arg)
		f := arg.(float32) // float32형변환
		return strconv.FormatFloat(float64(f), 'f', -1, 32)
	case float64:
		fmt.Println("float64 형 입니다.", arg)
		f := arg.(float64) // float64형변환
		return strconv.FormatFloat(f, 'f', -1, 64)
	case string:
		fmt.Println("string 형 입니다.", arg)
		s := arg.(string) // string형변환
		return s
	default:
		return "Error"
	}
}

func main() {
	fmt.Println(TypeCheck(1))
	fmt.Println(TypeCheck(1.1))
	fmt.Println(TypeCheck("hello"))

}

결과 화면

int 형 입니다. 1
1
float64 형 입니다. 1.1
1.1
string 형 입니다. hello
hello

 

 

 

반응형

'GO 언어' 카테고리의 다른 글

Echo framework로 간단한 웹서버 만들기  (1) 2022.03.27
유닛 테스트(Unit Test)  (0) 2022.03.09
모듈(Module)  (0) 2022.03.06
구조체(Struct)  (2) 2022.02.28
슬라이스(Slice)  (0) 2022.02.26
Comments