裏 RjpWiki

Julia ときどき R, Python によるコンピュータプログラム,コンピュータ・サイエンス,統計学

展開図上の反対側

2018年02月02日 | ブログラミング

展開図上の反対側

締め切りが 2018/02/02 10:00 AM なので,その 1 分後に投稿されるように予約

マス目を6つ指定します。
6つのマス目を立方体の展開図として組み上げた場合に、最初の面の反対側がどの面になるのかを計算してください。

【入出力】
入力は
glkmnq
のようになっています。

区切り文字なしで、面を示すアルファベット(図を参照)が6つ並んでいます。

出力するのは、最初の面の反対側の面のアルファベットです。
glkmnq
に対応する出力は、下図の通り、g の反対側は q なので
q
になります。

ただし、
jotfkpやklmngi
のように、
入力が立方体の展開図をなしていない場合は
-
を出力してください。

【例】
入力 glkmnq  出力 q

入力 klmngi  出力 -

入力 jotfkp  出力 -

入力 bcdhmr  出力 d


【補足】
    •    不正な入力に対処する必要はありません。
    •    ひとつながりになっていない場合は、展開図にはなっていないと判断してください。

========================================================

f = function(s) {
    abnormal = function(mat) {
        if (any(colSums(mat != " ") == 5, rowSums(mat != " ") == 5)) { # 縦(横)に5個並んでいる
            return(TRUE)
        }
        for (i in 1:4) { # 2行2列がある
            for (j in 1:4) {
                if (mat[i,j] != " " && mat[i+1,j] != " " && mat[i,j+1] != " " && mat[i+1,j+1] != " ") {
                    return(TRUE)
                }
            }
        }
        return(FALSE)
    }
    check = function(xy, m, n) { # (i, j) に隣接する面を辿って裏側になるものがあるかチェック
        a = array(xy, dim=c(2, m, n))
        for (k in 1:n) {
            ok = TRUE
            for (l in 1:m) {
                x = i+a[1, l, k]
                y = j+a[2, l, k]
                if (x < 1 || x > 5 || y < 1 || y > 5) {
                    ok = FALSE
                    break
                } else if (mat[x, y] == " ") {
                    ok = FALSE
                    break
                }
            }
            if (ok) {
                return(list(ok = TRUE, result = mat[x, y]))
            }
        }
        return(list(ok=FALSE, result=""))
    }
    letters = letters[1:25]
    t = unlist(strsplit(s, ""))
    mat = matrix(ifelse(letters %in% t, letters, " "), 5, byrow=TRUE)
    if (abnormal(mat)) { # 不正な展開図
        cat("-")
    } else {
        pos = grep(t[1], letters)-1
        i = pos %/% 5+1
        j = pos %% 5+1
        # B*E の場合(縦横の4方向) E が裏側
        # B の後の (i,j) の増分
        xy2 = c(0,-1,0,-2, -1,0,-2,0, 0,1,0,2, 1,0,2,0)
        a = check(xy2, 2, 4)
        if (a$ok) {
            cat(a$result)
            invisible()
        }
        # B
        # **
        #  E の場合 (8方向)
        xy3 = c(0,-1,1,-1,1,-2,
                0,-1,-1,-1,-1,-2,
                -1,0,-1,-1,-2,-1,
                -1,0,-1,1,-2,1,
                0,1,-1,1,-1,2,
                0,1,1,1,1,2,
                1,0,1,1,2,1,
                1,0,1,-1,2,-1)
        a = check(xy3, 3, 8)
        if (a$ok) {
            cat(a$result)
            invisible()
        }
        # B
        # ***
        #   E の場合 (8方向)
        xy4 = c(0,-1,1,-1,2,-1,2,-2,
                0,-1,-1,-1,-2,-1,-2,-2,
                -1,0,-1,-1,-1,-2,-2,-2,
                -1,0,-1,1,-1,2,-2,2,
                0,1,-1,1,-2,1,-2,2,
                0,1,1,1,2,1,2,2,
                1,0,1,1,1,2,2,2,
                1,0,1,-1,1,-2,2,-2)
        a = check(xy4, 4, 8)
        if (a$ok) {
            cat(a$result)
            invisible()
        }
        # B
        # ****
        #    E の場合 (8方向)
        xy5 = c(0,-1,1,-1,2,-1,3,-1,3,-2,
                0,-1,-1,-1,-2,-1,-3,-1,-3,-2,
                -1,0,-1,-1,-1,-2,-1,-3,-2,-3,
                -1,0,-1,1,-1,2,-1,3,-2,3,
                0,1,-1,1,-2,1,-3,1,-3,2,
                0,1,1,1,2,1,3,1,3,2,
                1,0,1,1,1,2,1,3,2,3,
                1,0,1,-1,1,-2,1,-3,2,-3)
        a = check(xy5, 5, 8)
        if (a$ok) {
            cat(a$result)
            invisible()
        }
    }
}
# f(readLines(file("stdin", "r")))

f("ngmbah") # g
f("rdmgch") # h
f("imdsen") # s
f("nuqprs") # u
f("gmknlr") # r
f("jbhaci") # h
f("ijcmbh") # b
f("gmlnrf") # r
f("nagihb") # b
f("pwrtsq") # -
f("fgbach") # -
f("mihgsn") # -

コメント    この記事についてブログを書く
  • X
  • Facebookでシェアする
  • はてなブックマークに追加する
  • LINEでシェアする
« 三角形に分割しよう | トップ | くたばれ Python »
最新の画像もっと見る

コメントを投稿

ブログラミング」カテゴリの最新記事