2023-02-05

Sean Kim·2023년 2월 5일
0

GoLang

목록 보기
3/5

출처: When to Use Generics in Go?. Introducing Go 1.18 generics and… | by Teiva Harsanyi | Medium

type parameter

  • 타입 파라미터는 메서드에서 쓸 수 없다.
	type Foo struct {}
	func (f Foo) bar[T any](t T) {}
	
    >>> methods cannot have type parameters
  • 타입 파라미터는 함수에만 쓸 수 있다.
	func getKeys[K comparable, V any](m map[K]V) []K {  
		var keys []K  
	    for k, v := range m {  
	        log.Printf("value %v of key is %v", v, k)  
	        keys = append(keys, k)  
	    }   
	    return keys  
	}
  • 구조체는 타입 파라미터를 받을 수 있다.
	type Node[T any] struct {
		Val T
		next *Node[T]
	}

	func (n *Node[T]) Add(next *Node[T]) {
		n.next = next
	}

when to use generics

  • ADT 구현시 사용할 수 있다. string, int, struct 벨류를 갖는 이진트리, 연결리스트, 힙 등
  • 다양한 타입을 가질 수 있는 slice, map, channel을 다뤄야할 때
  • 아래의 Interface는 go의 sort 패키지의 sort.go에 있는 IntSlice, Float64Slice, StringSlice 등의 타입이 각각 구현한 인터페이스인데, sliceFn같은 여러 타입을 수용할 수 있는 구조체를 만들어두면 sort.go 내부의 구현처럼 타입별로 하나하나 구현해줄 필요가 없어진다.
	type Interface interface {
		Len() int
		Less(i, j int) bool
		Swap(i, j int)
	}

	type sliceFn[T any] struct {
		s []T
		compare func(T, T) bool
	}

	func (s sliceFn[T]) Len() int { return len(s.s) }
	func (s sliceFn[T]) Less(i, k int) {return s.compare(s.s[i], s.s[j])}
	func (s sliceFn[T]) Swap(i, j int) {s.s[i], s.s[j] = s.s[j], s.s[i] }

when not to use generics

  • 단순히 type argument(타입 파라미터에 입력된 그 타입)의 메서드를 호출하는 경우
  • 아래의 경우 foo 함수에 어떤 타입이 입력되더라도 상관없이 그저 입력된 w에 입력된 byte를 쓸 분이다.
	func foo[T io.Writer](w T) {
		_, _ = w.Write([]byte("hello"))
	}
  • 이렇게 쓰면 된다.
	func foo(w io.Writer) {
		w.Write([]byte("hello"))
	}
  • 타입파라미터를 써서 코드의 가독성이 더 떨어질 때
profile
이것저것 해보고있습니다.

0개의 댓글