challenge 文字列の八方向検索

与えられた矩形状の文字列中に存在する文字列"ウオリ"の位置を全て出力するプログラムを
書いてください。
文字列の検索方向は八方全てで、また連続している(左右や上下の境界をまたがない)ものを
対象とします。出力は起点"ウ"の座標と方向のリストにしてください。

サンプル入力:

リオウウリウ
ウオリウオリ
オリリオリウ
リリオオウオ

サンプル出力:

(2, 0), 左
(0, 1), 右
(0, 1), 下
(3, 1), 右
(4, 3), 左上

--
より一般には、任意の検索文字列への対応も考えてみてください。

Posted feedbacks - C#

C#で。 動けばいいや的なコードです。

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.VisualBasic;

namespace どう書く_org文字列の八方向検索 {
    class Program {
        static string search;
        static List<string> list;
        static void Main(string[] args) {
            string sample = 
@"リオウウリウ
ウオリウオリ
オリリオリウ
リリオオウオ";
            search = "ウオリ";
            char[] sp = new char[] { '\n' };
            int width = sample.Split(sp)[0].Length;
            int height = sample.Split(sp).Length;
            list = new List<string>(sample.Split(sp));
            for(int y = 0; y < list.Count; y++) {
                for(int x = 0; x < list[y].Length; x++) {
                    if(list[y][x] == search[0]) {
                        if(E(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "右");
                        }
                        if(W(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "左");
                        }
                        if(S(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "下");
                        }
                        if(N(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "上");
                        }
                        if(NE(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "右上");
                        }
                        if(SE(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "右下");
                        }
                        if(NW(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "左上");
                        }
                        if(SW(x, y) == search) {
                            Console.WriteLine("(" + x + "," + y + ")" + "," + "左下");
                        }
                    }
                }
            }
            Console.ReadLine();
        }
        static string E(int x, int y) {
            try {
                return list[y].Substring(x, search.Length);
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string W(int x, int y) {
            try {
                return Strings.StrReverse(E(x - search.Length + 1, y));
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string S(int x, int y) {
            try {
                StringBuilder strb = new StringBuilder();
                for(int i = 0; i < search.Length; i++) {
                    strb.Append(list[y + i][x]);
                }
                return strb.ToString();
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string N(int x, int y) {
            try {
                return Strings.StrReverse(S(x, y - search.Length + 1));
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string SE(int x, int y) {
            try {
                StringBuilder strb = new StringBuilder();
                for(int i = 0; i < search.Length; i++) {
                    strb.Append(list[y + i][x + i]);
                }
                return strb.ToString();
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string NW(int x, int y) {
            try {
                return Strings.StrReverse(SE(x - search.Length + 1, y - search.Length + 1));
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string NE(int x, int y) {
            try {
                StringBuilder strb = new StringBuilder();
                for(int i = 0; i < search.Length; i++) {
                    strb.Append(list[y - i][x + i]);
                }
                return strb.ToString();
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
        static string SW(int x, int y) {
            try {
                return Strings.StrReverse(NE(x - search.Length + 1, y + search.Length - 1));
            } catch(ArgumentOutOfRangeException) { return ""; } catch(IndexOutOfRangeException) { return ""; }
        }
    }
}

皆さんと比べて長いんで、悔しくて短さに挑戦しました。まだまだ及びません…orz

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
//http://ja.doukaku.org/
//http://ja.doukaku.org/99/投稿用
using System;
using System.Collections.Generic;

namespace どう書く_org文字列の八方向検索 {
    class Program {
        static string search;
        static List<string> list;
        static void Main(string[] args) {
            string sample = "リオウウリウ\nウオリウオリ\nオリリオリウ\nリリオオウオ";
            search = "ウオリ";
            char[] sp = new char[] { '\n' };
            int width = sample.Split(sp)[0].Length;
            int height = sample.Split(sp).Length;
            list = new List<string>(sample.Split(sp));
            for(int y = 0; y < list.Count; y++) { //縦ループ
                for(int x = 0; x < list[y].Length; x++) { //横ループ
                    for(int dx = -1; dx <= 1; dx++) { //左右方向ループ
                        for(int dy = -1; dy <= 1; dy++) { //上下方向ループ -1は上、左 1は下、右を表す
                            try {
                                string strb = "";
                                for(int i = 0; i < search.Length; i++) { //iは移動量
                                    strb += list[y + i * dy][x + i * dx]; //移動方向をdy,dxで乗算することで反転
                                }
                                if(search == strb) {
                                    string directionStr = "";
                                    if(dx < 0) {
                                        directionStr += "左";
                                    } else if(dx > 0) {
                                        directionStr += "右";
                                    }
                                    if(dy < 0) {
                                        directionStr += "上";
                                    } else if(dy > 0) {
                                        directionStr += "下";
                                    }
                                    Console.WriteLine("(" + x + "," + y + ")" + "," + directionStr);
                                }
                            } catch(ArgumentOutOfRangeException) { } catch(IndexOutOfRangeException) { }
                        }
                    }
                }
            }
            Console.ReadLine();
        }
    }
}

"リリリ"の様な同じ文字が連続した文字列を検索すると不具合が出たので修正。 ついでに、何処まで行数を減らせるかテスト。可読性は二の次。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
class Program { //http://ja.doukaku.org/99/投稿用
    static void Main(string[] args) {
        string search = "ウオリ";
        System.Collections.Generic.List<string> list = new System.Collections.Generic.List<string>(new string[] { "リオウウリウ", "ウオリウオリ", "オリリオリウ", "リリオオウオ" });
        int width = list[0].Length; int height = list.Count;
        for(int y = 0; y < list.Count; y++) { //縦ループ
            for(int x = 0; x < list[y].Length; x++) { //横ループ
                for(int dx = -1; dx <= 1; dx++) { //左右方向ループ           -1は上、左 1は下、右を表す
                    for(int dy = -1; dy <= 1; dy = dy + (dx == 0 ? 2 : 1)) { //上下方向ループ 
                        try {                //dxが0の時はdyを2ステップして、両方が0にならないようにする                     
                            string strb = "";
                            for(int i = 0; i < search.Length; i++) { //iは移動量
                                strb += list[y + i * dy][x + i * dx];} //移動方向をdy,dxで乗算することで反転
                            if(search == strb) {
                                string directionStr = "";
                                if(dx < 0) directionStr += "左"; 
                                else if(dx > 0) directionStr += "右";
                                if(dy < 0) directionStr += "上";
                                else if(dy > 0) directionStr += "下";
                                System.Console.WriteLine("(" + x + "," + y + ")" + "," + directionStr);}
                        } catch(System.ArgumentOutOfRangeException) { } catch(System.IndexOutOfRangeException) { }}}}}
        System.Console.ReadLine();}}

Index

Feed

Other

Link

Pathtraq

loading...