[Golang] 변수

2021-09-22 hit count image

Golang에서 변수의 종류와 변수의 사용법에 대해서 알아봅시다.

개요

이번 블로그 포스트에서는 Golang에서 사용할 수 있는 변수의 종류에 대해서 살펴보고, 변수를 사용하여 코드를 작성하는 방법에 대해서 살펴보도록 하겠습니다.

이 블로그 포스트에서 소개하는 코드는 다음 링크를 통해 확인하실 수 있습니다.

변수

Golang의 변수에 대해서 살펴보기 위해 main.go 파일을 생성하고 다음과 같이 수정합니다.

package main

import "fmt"

func main() {
  var num int = 1
  var message string = "Hello, World!"
  fmt.Println(num, message)

  num = 2
  message = "Hello, Universe!"
  fmt.Println(num, message)
}

이렇게 수정하였다면, 다음 명령어를 실행하여 Golang으로 작성한 프로그램을 실행해 봅니다.

go run main.go

그럼 다음과 같은 결과를 확인할 수 있습니다.

1 Hello, World!
2 Hello, Universe!

변수 선언

Golang에서는 다음과 같이 변수를 선언합니다. Golang에서는 변수를 선언한 후, 변수를 사용하지 않으면 컴파일 에러가 발생합니다.

// var 변수명 변수타입 = 초기값
var num int = 1

변수를 선언할 때에는 var 키워드를 사용해야 하며, 어떤 타입에 변수가 저장될지 변수 타입을 지정해 줄 필요가 있습니다.

변수를 선언할 시, 다음과 같이 초기값을 설정하지 않고 생략할 수 있습니다.

var num int

다른 언어와는 다르게 Golang에서는 초기값을 설정하지 않으면 null이 저장되는 것이 아니라, 각 타입에 따른 기본값이 저장됩니다.

  • 모든 정수 타입(int, int8…): 0
  • 모든 실수 타입(float, float8…): 0.0
  • bool: false
  • 문자열: ""
  • 그 외: nil

초기값을 설정하는 경우 다음과 같이 변수 타입을 생략할 수 있습니다.

var num = 10

변수 타입을 생략하면, Golang은 초기값을 확인하여 타입 추론하게 됩니다.

마지막으로 다음과 같이 :=(Short variable declarations)을 사용하여 변수를 선언할 수 있습니다.

num := 10

타입 정의

Golang에서는 type 키워드를 사용하여, 기존의 타입에 별칭을 지정할 수 있습니다. 이를 Golang에서는 타입 정의(Defined type)라고 합니다.

type myInt int

Golang에서 제공하는 int 타입을 myInt으로 정의하였습니다. myIntint와 동일한 메모리 크기를 가지며 int와 동일한 역할을 수행하지만, int 타입과는 별개의 타입으로 존재하게 됩니다.

var myNum myInt = 10
var num int = 10

fmt.Printf("%T\n", myNum)
fmt.Printf("%T\n", num)

위와 같이 프로그램을 작성하고 실행해 보면, 다음과 같은 결과를 확인할 수 있습니다.

main.myInt
int

Golang에서는 타입이 서로 다른 경우, 연산을 수행할 수 없습니다. 따라서 연산을 수행하기 위해서는 타입 변환을 해야 합니다.

변수 타입

Golang에서는 다음과 같은 타입을 사용할 수 있습니다.

  • uint8, uint16, uint32, uint64
  • int8, int16, int32, int64
  • float32, float64
  • byte: uint8 별칭
  • rune: UTF8 형식 문자 한개를 저장할 때, 사용하는 변수, int32 별칭
  • int: int32 별칭
  • uint: uint32 별칭
  • bool
  • string
  • 배열
  • 슬라이스
  • 구조체
  • 포인터
  • 함수 타입
  • 인터페이스
  • 채널

타입 변환

앞서 이야기 했지만, Golang에서는 변수의 타입이 다르면 연산을 수행할 수 없다. 따라서 연산을 수행하기 위해서는 같은 변수 타입이 되도록 타입을 변환(Type Conversion)해 주어야 한다.

var num1 int = 10
var num2 int32 = 10

// fmt.Println(num1 + num2) // ERROR!!
fmt.Println(num1 + int(num2))

var num3 float32 = 10.32
fmt.Println(num1 + int(num3))

서로 다른 타입의 변수를 가지고 연산을 시도하면 컴파일 에러가 발생한다. 이때 타입 변환을 사용하여 같은 타입으로 변환 시킨 후 연산을 수행해야 합니다.

위에 코드를 실행시키면 다음과 같은 결과를 얻을 수 있다.

20
20

변수 스코프

Golang에서는 변수의 스코프(Scope)가 존재하며, 변수는 해당 스코프안에서만 사용이 가능하다. 스코프는 중괄호({})를 통해 표현한다.

func main() {
  num1 := 10

  {
    num2 := 20
    fmt.Println(num2)
  }

  fmt.Println(num1)
  // fmt.Println(num2) // ERROR!!
}

num1은 main 함수의 스코프에서 사용이 가능하지만, num2num1과 다르게 새로운 스코프 영역안에서만 사용이 가능하다. 따라서 하단에 fmt.Println(num2)num2를 가지고 있는 스코프밖에서 호출하였기 때문에 에러가 발생하게 된다.

패키지 전역 변수

Golang의 모든 소스 코드는 어떤 패키지에 소속되게 된다. 이때 함수 밖에 변수를 선언하게 되면, 패키지내에서 사용할 수 있는 패키지 전역 변수를 생성할 수 있다.

var num int = 10

func main() {
    fmt.Println(num)
}

패키지 전역 변수는 같은 패키지라면 어디에서든 사용이 가능하다.

빈칸 지시자

Golang에서는 선언한 변수는 반드시 사용해야 한다. 하지만, 변수를 할당은 해야 하지만 사용하지 않을 때 빈칸 지시자(Blank identifier, _)를 사용하여 에러를 피할 수 있다.

func main() {
  tmp := make(map[string]string)

  tmp["name"] = "John"
  tmp["job"] = "Programmer"

  fmt.Println(tmp)

  for k, v := range tmp {
    fmt.Println(k, v)
  }

  for k := range tmp {
    fmt.Println(k)
  }

  for _, v := range tmp {
    fmt.Println(v)
  }
}

위에 예제는 map 타입을 사용하여 변수를 생성한 후, 변수를 사용하는 다양한 방법을 보여주고 있습니다. mapmake를 사용하여 생성한 후, rangefor를 사용하여 모든 내용을 화면에 출력할 수 있습니다.

range를 사용하면 mapkeyvalue를 한번에 가져올 수 있습니다. keyvalue 모두 사용하고 싶을 때도 있지만, value만 사용하고 싶은 경우도 있습니다.

// ERROR!!
// for k, v := range tmp {
//     fmt.Println(v)
// }
for _, v := range tmp {
    fmt.Println(v)
}

이렇게 할당은 해야하지만, 사용하지 않을 때, 빈칸 지시자를 사용하여 컴파일 에러가 발생하지 않도록 할 수 있습니다.

완료

이것으로 Golang의 변수와 변수를 사용하는 방법에 대해서 기초적인 내용을 살펴보았습니다. 여기서 설명하지 않은 부분(map, slice의 사용법 등)은 다른 블로그 포스트에서 더욱 자세히 설명하도록 하겠습니다.

제 블로그가 도움이 되셨나요? 하단의 댓글을 달아주시면 저에게 큰 힘이 됩니다!

책 홍보

스무디 한 잔 마시며 끝내는 React Native 책을 출판한지 벌써 2년이 다되었네요.
이번에도 좋은 기회가 있어서 스무디 한 잔 마시며 끝내는 리액트 + TDD 책을 출판하게 되었습니다.

아래 링크를 통해 제가 쓴 책을 구매하실 수 있습니다.
많은 분들에게 도움이 되면 좋겠네요.

스무디 한 잔 마시며 끝내는 React Native, 비제이퍼블릭
스무디 한 잔 마시며 끝내는 리액트 + TDD, 비제이퍼블릭
Posts