기본 문법 요소들에 대해 알아보겠다. 이전에도 이야기했듯이 Go 는 코드 포맷에 대해 상당히 신경을 쓴다. 

1. 중괄호 { }, 소괄호 (), 세미콜론 ; 의 사용이 약간 다르다 (아래 참조)
2. Statement 들여쓰기 공백(space)은 탭으로 대체된다
3. 모든 코드는 UTF-8 기반 Unicode 이다.


▌세미콜론 ;

Go 는 ; 이 옵션이다. 있어도 되고 없어도 된다. 행여 쓰더라도 gofmt 를 돌리면 ; 은 삭제해버린다.
그러나 코드 작성 중에는 

fmt.Println("백 ");fmt.Println("입니다")
처럼 쓸 수 있다. 그러나 gofmt 를 돌리면 
fmt.Println("백 ")
fmt.Println("입니다")
이렇게 세미콜론을 없애고 두줄로 바뀐다.

▌중괄호 {}

중괄호는 반드시 inline 으로 시작하여야 한다. 다음줄에서 시작하면 오류다. 또한 if 문의 경우 else 문은 반드시 닫는 중괄호 } 뒤에 inline 으로 와야 한다.

package main

import "fmt"

func main(){
       some := 100
       if (some == 100) {
              fmt.Println("백 ");fmt.Println("입니다")
       } else {
              fmt.Println("뭥미")
       }

       for i:=i<10 i++ {
              fmt.Println("==> "i)
       }
}

▌소괄호 ()

소괄호는 함수가 아닌 경우 사용하지 않는다. 사용해도 무방하지만 gofmt 를 돌리면 이 역시 날아간다
위 코드를 gofmt 를 적용한 결과는

package main

import "fmt"

func main() {
       some := 100
       if some == 100 {
              fmt.Println("백 ")
              fmt.Println("입니다")
       } else {
              fmt.Println("뭥미")
       }

       for i := 0i < 10i++ {
              fmt.Println("==> "i)
       }
}

어찌 보면 이게 더 코드 가독성을 떨어뜨리는것 같기도 하지만, 함수 호출이 눈에 좀더 들어오기는 한다.

▌변수 선언

변수 선언은 아래 방법이 있다

var <변수> = <값> 를 사용한 자동 타입 결정 선언
var <변수> <타입> 을 사용한 명시적 타입 변수 선언
var <변수> [타입] [= <값>] 을 사용한 명시적 타입의 변수 선언 및 할당
<변수> := <값> 을 사용한 자동 변수 선언 및 값에 의한 타입 결정 후 할당

여러 변수 선언 방법은 
var <변수>[,<변수>,…] = <값> [,<값>,…]
var <변수>[,<변수>,…] <타입>
var (
     <위 여러 변수 선언 방법에서 var 키워드를 제외한 부분과 동일>
     [, <변수선언>]
     […]
)

/**
변수 선언 예제
*/
package main

import "fmt"

func main() {
       // 변수 선언 예제
       var val1 = "1"
       var val2 int
       var val3 int 3
       val4 := 0x04

       // 여러 변수 동시 선언
       var val5val6 = "5"6
       var val7val8 int
       var val9val10 int 910
       val11val12 := 11"12"

       var (
              val13val14 int 1314
              val15val16 = "15"16
       )
}

그런데 위 코드를 빌드하면 에러가 발생한다

1. “fmt” 를 import 하였으나 사용하지 않았음
2. 모든 변수를 선언하였으나 사용하지 않았음

다른 언어에서는 그냥 Warning 으로 지나칠것을 Go 에서는 에러로 간주한다. 이때에는 _ 를 사용하여 이러한 에러를 내지 않도록 할 수 있다.

import 문
import "fmt"

사용하지 않은 변수 에러 회피
var val1 = "1"
_ = val1

위 처럼 _ 를 사용하여 에러를 회피 가능하나 좋은 방법은 아니다.

▌숫자형 데이터 타입

uint8       the set of all unsigned  8-bit integers (to 255)
uint16      the set of all unsigned 16-bit integers (to 65535)
uint32      the set of all unsigned 32-bit integers (to 4294967295)
uint64      the set of all unsigned 64-bit integers (to 18446744073709551615)

int8        the set of all signed  8-bit integers (-128 to 127)
int16       the set of all signed 16-bit integers (-32768 to 32767)
int32       the set of all signed 32-bit integers (-2147483648 to 2147483647)
int64       the set of all signed 64-bit integers (-9223372036854775808 to 9223372036854775807)

float32     the set of all IEEE-754 32-bit floating-point numbers
float64     the set of all IEEE-754 64-bit floating-point numbers

complex64   the set of all complex numbers with float32 real and imaginary parts
complex128  the set of all complex numbers with float64 real and imaginary parts

byte        alias for uint8
rune        alias for int32


32bit 플랫폼은 int, uint = int32, uint32
64bit 플랫폼은 int, uint = int64, uint64 이다
float 타입은 플랫폼에 상관없이 32 나 64 를 직접 지정해줘야 한다

생소한 타입은 float64, complex64, complex128, rune 정도이다.
float64 : 64bit 의 float 이다
complex64 : float32 의 실수 + 32비트 허수부로 구성된 복소수
complex128 : float64 의 실수 + 64비트 허수부로 구성된 복소수


▌정수

정수는 크게 다를게 없으므로 Pass

▌실수

다른 언어와 마찬가지로 부동 소수점 방식으로 저장됨. 
지수는 e, E 로 표기하며 + 또는 - 이후에 소수점 위치를 나타냄

var val1 float64 0.1
var val2 float64 .2
var val3 float64 3.3123e3
var val4 float64 4.4123e+5
var val5 float64 5.5123e-5

val3 => 3312.3
val4 => 441230
val5 => 0.00005123

실수 연산의 오차율
실수 연산 시 Go 언어의 실수 오차범위는 1e-14 임. 값 비교 시 실수 값의 실수부 차를 제외한 값의 차이가 1e-14 이내이면 같은 실수값으로 보아야 하며, 비교시에는 math 패키지의 abs() 를 통해 비교해야 부호에 의한 오판 없음

▌복소수 (Complex)

실수부 + 허수부 로 표현되는 복소수. 고정소수점 과 부동소수점 으로 표현함.
복소수를 변수에 저장할때에는 실수부 또는 허수부 생략 가능함.

일단, 복소수의 수학적 개념을 보면

머리가 아플수도 있지만 허수 계산이 필요한 경우 이 complex 타입을 사용한다.


complex 타입을 위한 함수
real() : complex 에서 실수부 가져옴
imag() : complex 에서 허수부 가져옴

표현 방법:
var <변수> complex32 = <실수부> + <허수부>i 또는 complex(<실수부>, <허수부>) 로 표현

var val0 complex128 1.123e-4 2.234e+3i // 실수와 허수 모두 입력 
var val1 complex128 2.234e+3i
var val2 complex128 2.234e+3i // 허수부만 입력
var val3 complex128 complex(1.123e-42.234e+3i// complex() 로 입력

var rVal1 float64 real(val1) // 실수부
var iVal1 float64 imag(val1) // 허수부

위 처럼 표현 가능함

▌rune

UTF-8 character 를 저장하기 위한 타입. 값은 char 처럼 ‘ ‘ 로 묶어줌.

var val1 rune '굿'
var val2 = '준'
var val3 rune '\uAD7F'
val4 := '\uC900'

fmt.Println(val1" "val2)
fmt.Println(val3" "val4)
fmt.Printf("%c%c"val3val4)

실행결과
44415   51456
44415   51456
굿준

▌형변환

Go 는 암시적(자동) 형변환을 제공하지 않는다. 명시적인 형변환은 <타입>(<값>) 형태로 하면 된다.

아래 코드는 오류가 발생한다.
package main

import "fmt"

func main() {
   var val1 int64 1000000
   var val2 float32 1.234e-3

   var res = val1 + val2

   fmt.Println(res)
}

위 코드를
var res = float32(val1) + val2
처럼 수정해야 에러가 나지 않는다.

정수와 소수의 최소/최대 크기는 math 패키지의 정의로 확인할 수 있다
// int
fmt.Println(math.MinInt16)
fmt.Println(math.MaxInt16)
fmt.Println(math.MinInt32)
fmt.Println(math.MaxInt32)
fmt.Println(math.MinInt64)
fmt.Println(math.MaxInt64)

// float
fmt.Println(math.MaxFloat32)
fmt.Println(math.MaxFloat64)

결과는
-32768
32767
-2147483648
2147483647
-9223372036854775808
9223372036854775807
3.4028234663852886e+38
1.7976931348623157e+308

이외에, 변수의 Size 를 알아보려면 unsafe 패키지의 Sizeof() 를 사용하면 된다.

▌문자열

string 타입을 사용한다. + 연산자 사용 가능, == 연산자로 문자열 비교
len() 으로 전체 size 가져옴. utf8 패키지로 utf8 문자열의 카운팅 등

package main

import (
   "fmt"
   "unicode/utf8"
)

func main() {
   var str1 string "goodjoon.tistory.com "
   var str2 string `굿준 블로그`
   var str3 string `
어서 오세요
환영합니다` // 여러줄을 사용

   fmt.Println(str1" - "str2str3)
   fmt.Println("len str1 : "len(str1)) // len() 을 사용하면 문자열 전체 바이트 수 가져옴
   fmt.Println("len str2 : "len(str2))
   // utf8 패키지 사용하여 utf8 문자열의 문자 수 카운트
   fmt.Println("RuneCountInString(str1) : "utf8.RuneCountInString(str1))
   fmt.Println("RuneCountInString(str2) : "utf8.RuneCountInString(str2))

   fmt.Println(" + : "str1 + " - " + str2) // + 연산자
   fmt.Println(" == "str2 == "굿준 블로그"" / "str1 == str2) // Go 는 == 로 문자열 비교함
   fmt.Println("str1[1]"str1[1]) // 배열로 문자열 []byte 를 접근함. 수정은 불가함 read-only
   fmt.Println("str2[1]"str2[1])
   for i:=i<len(str2) i++ {
      fmt.Printf("%x|",str2[i])
   }
}

결과
/usr/local/go/bin/go run /Users/korean44/src/go_workspace/src/Grammar1/string_type.go
goodjoon.tistory.com   -  굿준 블로그 
어서 오세요
환영합니다
len str1 :  21
len str2 :  16
RuneCountInString(str1) :  21
RuneCountInString(str2) :  6
 + :  goodjoon.tistory.com  - 굿준 블로그
 ==  true  /  false
str1[1] 111
str2[1] 181
ea|b5|bf|ec|a4|80|20|eb|b8|94|eb|a1|9c|ea|b7|b8|


▌상수 및 Enumeration

C/C++ 처럼 const 로 상수 만듦. 
const 로 선언하는 문자열은 var 키워드를 붙이지 않음.
iota 키워드를 사용하면 const 선언 내에서 1씩 증가하는 수가 생성됨
const 변수는 선언하고 사용하지 않아도 에러 나지 않음

package main

import "fmt"

const CONST_NUM 100
const CONST_STR string "굿준"
const (
   RED int 0
   GREEN int 1
   BLUE int 2
)
const (
   ZERO iota       // 0 부터 시작하며 하나씩 증가
   ONE
   TWO
   THREE
   FOUR
)
const (
   HANA 0
   DUL
   SET
)

func main() {
   fmt.Println(CONST_STR)
   fmt.Println(GREEN)
   fmt.Println(THREE)
   fmt.Println(DUL)
}



▌연산자

나머지는 다른 언어들과 동일하며, 몇가지 연산자만 추가설명

&^ : AND 연산 값을 NOT 연산 함 

func main() {
   var val1 byte 0x70 // 0111 0000
   var val2 byte 0x11 // 0001 0001
   var val3,val4 = 0x700x11

   fmt.Println("==== Bit Operator ====")
   fmt.Printf("%08b\n"val1 ^ val2) // XOR 연산
   fmt.Printf("%08b\n"^val1)
   // &^ : 좌항과 XOR 연산 값을 다시 좌항과 AND 연산 함 (좌항 값의 Bit Clear)
   fmt.Printf("%08b\n"val1 &^ val2)
   fmt.Printf("%08b\n"(val1 ^ val2) & val1) // &^ 과 같음
   val3 &^= val4
   fmt.Printf("%08b\n"val3)

   // Pointer 관련 연산자
   var val5 = 10
   var ref1 = &val5

   fmt.Println("==== Pointer ====")
   fmt.Printf("%d\n",*ref1)
   fmt.Printf("val5's address : %x / ref1's value : %x"&val5ref1)
   
}

결과
==== Bit Operator ====
01100001
10001111
01100000
01100000
01100000
==== Pointer ====
10
val5's address : c82000a2a8 / ref1's value : c82000a2a8



반응형

'Software Development > Go (golang)' 카테고리의 다른 글

3.4 Go - 제어문  (1) 2016.03.01
3.3 Go - Package  (0) 2016.03.01
3.1 Go - Hello World  (0) 2016.02.29
2. Go - 개발환경 구성  (0) 2016.02.28
1.3 Go 언어란? - 다른 언어와 비교  (0) 2016.02.28
블로그 이미지

Good Joon

IT Professionalist Since 1999

,