이 페이지는 코딩도장 데이터의 읽기 전용 정적 보관본입니다.

fill 게임

  1. 왼쪽 위에서부터 빈 곳을 채우세요. (O:빈곳, X:비어있지 않은곳)
  2. 가능한 경우를 모두 출력하세요 (R:오른쪽, L:왼쪽, D:아래쪽, U:위쪽)
      input:
      OOOOO
      XOOXO
      OOOOO
      OOOOO
      OOOOX

      output:
      1 :
      RRRRD
      XDLXD
      DLULL
      DRDRO
      RURUX

      ...

      12 :
      RDRRD
      XDUXD
      DLULD
      DRDUO
      RURUX


재귀 트랙백

2018/08/24 11:18

박범수

7개의 풀이가 있습니다.

RLUD 대신 화살표(?)로 해 봤습니다.

def find_path(x, y, move_cnt):
    global map_, X, Y, MAX_MOVE

    if move_cnt >= MAX_MOVE:
        for row in map_:
            print(''.join(row))
        print()
    else:
        for dx, dy, dir_ch in [(0, -1, '<'), (0, 1, '>'), (1, 0, 'v'), (-1, 0, '^')]:
            x2, y2 = x + dx, y + dy
            if 0 <= x2 < X and 0 <= y2 < Y and map_[x2][y2] is 'O':
                map_[x][y] = dir_ch
                find_path(x2, y2, move_cnt + 1)
                map_[x][y] = 'O'


map_ = [list(row) for row in input_str.split('\n')]
X, Y= len(map_), len(map_[0])
MAX_MOVE = X * Y - input_str.count('X') - 1
find_path(0, 0, 0)

2018/08/25 00:42

Noname

def _find_start_point():
  for i,j in enumerate(board):
    if 'O' in j: return i, j.index('O')
  print('시작점을 찾을 수 없음')

def print_board():
  for i in board: print(''.join(i))
  print()

def fillgame():
  dr = ((0,1,'R'), (1,0,'D'), (0,-1,'L'), (-1,0,'U'))
  stc = [[_find_start_point(), -1]]
  while stc:
    stc[-1][1] += 1
    if stc[-1][1] < 4:
      dx, dy, s, x, y = *dr[stc[-1][1]], *stc[-1][0]
      if 0<= x+dx <len(board) and 0<= y+dy <len(board[0]) and board[x+dx][y+dy] == 'O':
        board[x][y] = s
        stc.append([(x+dx, y+dy), -1])

      if str(board).count('O') == 1:
        yield
        stc.pop()
        board[x][y] = 'O'
    else:
      x, y = stc[-1][0]
      board[x][y] = 'O'
      stc.pop()



test = '''\
OOOOO
XOOXO
OOOOO
OOOOO
OOOOX'''

board = [list(i) for i in test.splitlines()]
for i,j in enumerate(fillgame()):
  print(i+1,':')
  print_board()

2018/08/25 21:54

Creator

Ruby

trav = ->r,c,maze do
  return [maze] if maze.join.count("O") == 1
  [["D", r+1,c], ["U", r-1,c], ["L", r,c-1], ["R", r,c+1]].
    select {|_,*pos| pos.none?(&:negative?) && maze[pos[0]] && maze[pos[0]][pos[1]] == "O"}.
    map {|log,*pos| pos << maze.map(&:dup).tap {|e| e[r][c] = log}}.flat_map {|e| trav[*e]}
end
find_trails = ->maze { puts trav[0, 0, maze.split].map.with_index(1) {|t,i| ["#{i} :", t, ""]}}

Test

input = <<-eos
OOOOO
XOOXO
OOOOO
OOOOO
OOOOX
eos

end_of_result = <<-eos
12 :
RRRRD
XDLXD
DLULL
DRDRO
RURUX

eos

# output(.. ending_with..).to_stdout은 rspec test framework의 matcher들 입니다.
expect { find_trails[input] }.to output(a_string_ending_with(end_of_result)).to_stdout

2018/09/03 07:06

rk

from copy import deepcopy

map_ ='''OOOOO
XOOXO
OOOOO
OOOOO
OOOOX'''

map_list_1 = [list(i) for i in map_.split('\n')]

def check(data) :  # 완료 여부 확인
    count = 0
    for line in data[:-1] :
        if 'O' in line : count += line.count('O')
    if count <= 1 : return True
    else : return False

def search_(li) :
    queue, count = [li+[[0, 0]]], 0
    while len(queue) != 0 :
        head = queue.pop(0)
        if check(head) == True :  # 성공적으로 탐색을 완료한 경우 그 결과를 출력
            count += 1
            print('\n\n'+str(count)+':')
            for RL in head[:-1] :
                print(''.join(RL))
            head = 0
            continue
        for cond in [(-1, 0, 'L', head[-1][0]), (1, 0, 'R', len(head[0])-1-head[-1][0]), (0, -1, 'U', head[-1][1]), (0, 1, 'D', len(head)-2-head[-1][1])] :  # 순서대로 dx, dy, 방향, 좌표가 데이터 범위 내 있을 조건
            head_1 = deepcopy(head)
            if cond[3] > 0 and head_1[head_1[-1][1]+cond[1]][head_1[-1][0]+cond[0]] == 'O' : # 좌표가 데이터 범위 내에 있으면서 탐색 가능한 경우
                head_1[head_1[-1][1]][head_1[-1][0]] = cond[2] #'O'값 방향으로 대체
                head_1[-1][0], head_1[-1][1] = head_1[-1][0]+cond[0], head_1[-1][1]+cond[1] #좌표 갱신
                queue.append(head_1) # queue의 마지막에 추가
search_(map_list_1)

queue를 활용하였습니다. mutable한 객체에 대한 개념이 없었는데 이 문제 덕분에 아주 좋은 것을 배웠습니다.

결과중 처음 것만 아래에 작성하겠습니다.

1:
RRRRD
XDLXD
DLULL
DRDRO
RURUX

2020/01/29 14:49

GG

inp="""OOOOO
XOOXO
OOOOO
OOOOO
OOOOX"""
lst=[list(ln) for ln in inp.split("\n")]
maxX,maxY=len(lst[0]),len(lst) #x축의 길이, y축의 길이
notry,nom=0,0 #시행 차수, 움직인 횟수
maxmove=maxX*maxY-inp.count("X")-1 #최대로 움직일 수 있는 횟수=x축 길이*y축 길이-격자의 X 개수-마지막 O 1개
def solve(y,x):
    global maxX,maxY,notry,maxmove,nom
    if nom==maxmove: #움직인 횟수가 최대 움직일 수 있는 횟수와 같으면 시행 차수를 +1하고 출력
        notry+=1
        print(notry)
        for ln in lst:
            for cmp in ln:
                print("%1s"%cmp, end="")
            print()
    else:
        for dx,dy,dr in [(1,0,"R"),(-1,0,"L"),(0,1,"D"),(0,-1,"U")]:
            nx,ny=x+dx,y+dy
            if 0<=nx<maxX and 0<=ny<maxY and lst[ny][nx]=="O":
                lst[y][x],nom=dr,nom+1
                solve(ny,nx)
                lst[y][x],nom="O",nom-1
solve(0,0)

2020/09/03 10:58

박시원

// Rust

// 어쨌든 결과는 나오네요...

fn lattice_fill() {

let lattice = "OOOOO
XOOXO
OOOOO
OOOOO
OOOOX";
let mut arr = vec![];
for line in lattice.lines() {
    arr.push(line.trim().chars().collect::<Vec<_>>());
}
if let Some(_) = step(arr, (0,0)) {
}

} fn step(arr_:Vec>, (i, j): (usize, usize)) -> Option>> {

let mut arr = arr_.clone();
let l = arr.len();
let mut action = vec![];
if i==0 {
    if arr[i+1][j] == 'O' {action.push('D');}}
else if i==l-1 {
    if arr[i-1][j] == 'O' {action.push('U');}}
else {
    if arr[i+1][j] == 'O' {action.push('D');}
    if arr[i-1][j] == 'O' {action.push('U');}}
if j==0 {
    if arr[i][j+1] == 'O' {action.push('R');}}
else if j==l-1 {
    if arr[i][j-1] == 'O' {action.push('L');}}
else {
    if arr[i][j-1] == 'O' {action.push('L');} 
    if arr[i][j+1] == 'O' {action.push('R');}}

if action.is_empty() {
    let mut cnt=0;
    for line in &arr { cnt += line.iter().filter(|&c| *c=='O').count();}       
    if cnt <= 1 {
        println!("{:?}", (i,j));
        print_vec(&arr);
        return Some(arr.clone());} //ok
    else { return None;} //fail
}
for a in action {
    arr[i][j] = a;
    if a=='U' { 
        if let Some(_) = step(arr.clone(), (i-1, j)) {}}
    else if a=='D' {
        if let Some(_) = step(arr.clone(), (i+1, j)) {}}
    else if a=='L' { 
        if let Some(_) = step(arr.clone(), (i, j-1)) {}}
    else { 
        if let Some(_) = step(arr.clone(), (i, j+1)) {}}
}
None

} fn print_vec(vec: &Vec>) {

for line in vec {
    let mut result = String::new();
    result.extend(line);
    println!("{}", result);
}

}

2022/02/02 09:29

JW KIM

using System;

namespace solution
{
    class Program
    {
        public static int maxRow;
        public static int maxCol;
        public static int maxCnt;
        public static int N;

        static void Main(string[] args)
        {
            char[,] input = { {'O','O','O','O','O'}, {'X','O','O','X','O'},
                {'O','O','O','O','O' }, {'O','O','O','O','O' }, {'O','O','O','O','X' } };
            maxRow = 5;
            maxCol = 5;
            maxCnt = maxRow * maxCol;
            for (int r = 0; r < maxRow; r++)
            {
                for (int c = 0; c < maxCol; c++)
                    if (input[r, c] == 'X')
                        maxCnt--;
            }
            N = 1;
            findPath(0, 0, 1, input);
        }

        private static void findPath(int r, int c, int cnt, char[,] input)
        {
            if(cnt >= maxCnt)
            {
                printInput(input);
                return;
            }
            int[] dr = { -1, 0, 1, 0 };
            int[] dc = { 0, 1, 0, -1 };
            char[] dir = { 'U', 'R', 'D', 'L' };
            for (int i = 0; i < 4; i++)
            {
                int R = r + dr[i];
                int C = c + dc[i];
                if(0<=R && R<maxRow && 0<=C && C<maxCol && input[R, C] == 'O')
                {
                    input[r, c] = dir[i];
                    findPath(R, C, cnt + 1, input);
                    input[r, c] = 'O';
                }
            }
        }

        private static void printInput(char[,] input)
        {
            Console.WriteLine("\n  {0} :", N++);
            for (int r = 0; r < maxRow; r++)
            {
                for (int c = 0; c < maxCol; c++)
                {
                    Console.Write(" {0}", input[r,c]);
                }
                Console.WriteLine();
            }
        }
    }
}

2023/09/01 20:41

insperChoi

목록으로