Spiral Array

문제는 다음과 같다:

6 6

  0   1   2   3   4   5
 19  20  21  22  23   6
 18  31  32  33  24   7
 17  30  35  34  25   8
 16  29  28  27  26   9
 15  14  13  12  11  10

위처럼 6 6이라는 입력을 주면 6 X 6 매트릭스에 나선형 회전을 한 값을 출력해야 한다.

※ 상대에게 상처를 주기보다 서로에게 도움이 될 수 있는 댓글을 달아 주세요.

1개의 풀이가 있습니다.

package main

import (
    "fmt"
    "os"
)

type Dir int

const INVALID_INDEX = -1

const (
    RIGHT Dir = iota
    DOWN
    LEFT
    UP
)

type Board struct {
    width, height int
    data [][]int
}

func NewBoard(width, height int) *Board {
    b := Board{}
    b.width = width
    b.height = height
    b.data = make([][]int, height)
    for i := 0; i < height; i++ {
        b.data[i] = make([]int, width)
    }

    for j := 0; j < height; j++ {
        for i := 0; i < width; i++ {
            b.data[j][i] = INVALID_INDEX
        }
    }

    return &b
}

func (b *Board) Valid(x, y int) bool {
    if x < 0 || x >= b.width || y < 0 || y >= b.height {
        return false
    }

    if (b.data[y][x] != INVALID_INDEX) {
        return false
    }

    return true
}

func (b *Board) Show() {
    for j := 0; j < b.height; j++ {
        for i := 0; i < b.width; i++ {
            fmt.Printf("%3d ", b.data[j][i])
        }
        fmt.Println()
    }
}

type Object struct {
    x, y int
    dir Dir
    index int
    board *Board
}

func NewObject(b *Board) *Object {
    o := Object{}
    o.board = b
    return &o
}

func (o *Object) Put() {
    o.board.data[o.y][o.x] = o.index
    o.index++
}

func (o *Object) Turn() {
    o.dir++
    o.dir %= 4
}

func (o *Object) Advance() bool {
    tx := o.x
    ty := o.y

    switch o.dir {
    case UP: ty--
    case DOWN: ty++
    case LEFT: tx--
    case RIGHT: tx++
    }

    if (o.board.Valid(tx, ty)) {
        o.x = tx
        o.y = ty
        return true
    } else {
        return false
    }
}

func main()  {
    width := 0
    height := 0

    fmt.Printf("Input board width: ")
    fmt.Fscanf(os.Stdin, "%d", &width)

    fmt.Printf("Input board height: ")
    fmt.Fscanf(os.Stdin, "%d", &height)

    board := NewBoard(width, height)
    obj := NewObject(board)

    for {
        obj.Put()
        if (obj.Advance() == false) {
            obj.Turn()
            if (obj.Advance() == false) {
                break;
            }
        }
    }

    board.Show()
}
※ 상대에게 상처를 주기보다 서로에게 도움이 될 수 있는 댓글을 달아 주세요.

풀이 작성

※ 풀이작성 안내
  • 본문에 코드를 삽입할 경우 에디터 우측 상단의 "코드삽입" 버튼을 이용 해 주세요.
  • 마크다운 문법으로 본문을 작성 해 주세요.
  • 풀이를 읽는 사람들을 위하여 풀이에 대한 설명도 부탁드려요. (아이디어나 사용한 알고리즘 또는 참고한 자료등)
  • 작성한 풀이는 다른 사람(빨간띠 이상)에 의해서 내용이 개선될 수 있습니다.
목록으로
코딩도장

코딩도장은 프로그래밍 문제풀이를 통해서 코딩 실력을 수련(Practice)하는 곳입니다.


언어별 풀이 현황
전 체 x 146
기 타 x 17
java x 31
cpp x 35
python x 45
lisp x 2
ruby x 2
cs x 6
scala x 3
clojure x 1
objectivec x 1
go x 1
delphi x 1
javascript x 1