Printing string in rows and column pattern Java

前端 未结 7 2257
孤独总比滥情好
孤独总比滥情好 2021-02-07 14:31

i\'m just created a java project to print string that is given in rows and column just like matrix. Here\'s the output that i just made:

h e l l o 
_ w o r l 
d _         


        
相关标签:
7条回答
  • 2021-02-07 15:15

    Probably I'll add my answer too, idea is to flatten a two dimensional array to 1d and use the 1D array and transform it to a 2D spiral array. Hope it helps.

    Code:

    class Test {
    
        static String[][] spiralPrint(int m, int n, String[] a) {
            String[][] output = new String[m][n];
            int count = 0;
            int i, k = 0, l = 0;
            while (k < m && l < n) {
                for (i = l; i < n; ++i) {
                    output[k][i] = a[count++];
                }
                k++;
    
                for (i = k; i < m; ++i) {
                    output[i][n - 1] = a[count++];
                }
                n--;
    
                if (k < m) {
                    for (i = n - 1; i >= l; --i) {
                        output[m - 1][i] = a[count++];
                    }
                    m--;
                }
    
                if (l < n) {
                    for (i = m - 1; i >= k; --i) {
                        output[i][l] = a[count++];
                    }
                    l++;
                }
            }
            return output;
        }
    
        private static String[] flattenArray(String[][] input, int m, int n) {
            String[] output = new String[m * n];
            int k = 0;
            for (int i = 0; i < m; i++) {
                for (int j = 0; j < n; j++) {
                    output[k++] = input[i][j];
                }
            }
            return output;
        }
    
        public static void main(String[] args) {
    
            String[][] input = {
                    {"h", "e", "l", "l", "o"},
                    {"_", "w", "o", "r", "l"},
                    {"d", "_", "i", "t", "s"},
                    {"_", "b", "e", "a", "u"},
                    {"t", "i", "f", "u", "l"}};
    
            int m = 5;
            int n = 5;
    
            String[] flattenArray = flattenArray(input, m, n);
            String[][] spiralArray = spiralPrint(m, n, flattenArray);
    
            for (int i = 0; i < m; i++) {
                for (int j = 0; j < n; j++) {
                    System.out.print(spiralArray[i][j] + " ");
                }
                System.out.println();
            }
    
        }
    }
    
    Output:
    h e l l o 
    _ b e a _ 
    s u l u w 
    t f i t o 
    i _ d l r 
    

    Note: Indeed that I followed this Spiral transform to 1D, but it is not straight forward, I have re-modified to fit to the problem.

    0 讨论(0)
  • 2021-02-07 15:15

    When can't go straight turn left to walk, this is the theory used in this solution

    int dr[] = {0, 1, 0, -1};
    int dc[] = {1, 0, -1, 0};
    

    this is used for always move pattern. And curr & curc represent current position and curm represent current move pattern.

      public int[][] solve(int r, int c, String s) {
        int m[][] = new int[5][5];
        int curr = 0, curc = 0;
        
        for (int pos = 0, curm = 0; pos < r*c; pos++) {
          m[curr][curc] = (int) s.charAt(pos);
          if (curr + dr[curm] < 0 || curr + dr[curm] >= r || curc + dc[curm] < 0 || curc + dc[curm] >= c
              || m[curr + dr[curm]][curc + dc[curm]] != 0)
            curm = (curm + 1) % 4;
          curr = curr + dr[curm];
          curc = curc + dc[curm];
        }
        return m;
      }
    

    Then you can print this way

    for (int i = 0; i < r; i++) {
      for (int j = 0; j < c; j++) {
        System.out.printf("%c ", m[i][j]);
      }
      System.out.println("");
    }
    
    0 讨论(0)
  • 2021-02-07 15:17

    I think that the best way to implement this is the following:

    1. create an instruction object (Dictionary.java) which controls the fill-in process of the matrix
    2. fill in the matrix with data (Spiral.java)
    3. then show the matrix

    With this approach, you can change the pattern easily, without changing the rest of the code because the pattern generator works detached from the rest of the code.

    This is how the basic Dictionary class may look like:

    public abstract class Dictionary {
    
        protected int matrixSize;
        protected String[] dictionary;
    
        public Dictionary(int matrixSize) {
            this.matrixSize = matrixSize;
            dictionary = new String[matrixSize * matrixSize];
        }
    
        public abstract String[] createPattern();
    
        public void showPattern() {
            Arrays.stream(dictionary).forEach(System.out::println);
        }
    }
    

    For each pattern, you need to implement the createPattern() method differently. For example, a frame pattern implementation can be something like this:

    public class FrameDictionary extends Dictionary {
    
        protected int dictionaryIndex = 0;
        protected int startX, endX;
        protected int startY, endY;
    
        public FrameDictionary(int matrixSize) {
            super(matrixSize);
            startX = -1;
            endX = matrixSize - 1;
            startY = 0;
            endY = matrixSize - 1;
        }
    
        @Override
        public String[] createPattern() {
            while (dictionaryIndex < matrixSize) {
                pattern1();
                pattern2();
            }
            return dictionary;
        }
    
        /**
         * pattern 1
         * direction: left -> right then top -> bottom
         */
        protected void pattern1() {
            startX++;
            for (int i = startX; i <= endX; i++) {
                dictionary[dictionaryIndex] = i + ":" + startY;
                dictionaryIndex++;
            }
    
            startY++;
            for (int i = startY; i <= endY; i++) {
                dictionary[dictionaryIndex] = endX + ":" + i;
                dictionaryIndex++;
            }
        }
    
        /**
         * pattern 2
         * direction: right -> left then bottom -> top
         */
        protected void pattern2() {
            endX--;
            for (int i = endX; i >= startX; i--) {
                dictionary[dictionaryIndex] = i + ":" + endY;
                dictionaryIndex++;
            }
    
            endY--;
            for (int i = endY; i >= startY; i--) {
                dictionary[dictionaryIndex] = startX + ":" + i;
                dictionaryIndex++;
            }
        }
    }
    

    Output:

    a b c d e f
    t         g
    s         h
    r         i
    q         j
    p o n m l k
    

    You can draw the pattern what you need with the following implementation of the createPattern() method:

    public class ClockWiseDictionary extends FrameDictionary {
    
        public ClockWiseDictionary(int matrixSize) {
            super(matrixSize);
        }
    
        @Override
        public String[] createPattern() {
            int pixelsInMatrix = matrixSize * matrixSize;
            while (dictionaryIndex < pixelsInMatrix) {
                pattern1();
                pattern2();
            }
            return dictionary;
        }
    }
    

    Output:

    a b c d e f
    t u v w x g
    s 6 7 8 y h
    r 5 0 9 z i
    q 4 3 2 1 j
    p o n m l k
    

    Or just for fun, a "snake" pattern implementation:

    public class SnakeDictionary extends Dictionary {
    
        private int dictionaryIndex = 0;
        private int startY = 0;
    
        public SnakeDictionary(int matrixSize) {
            super(matrixSize);
        }
    
        @Override
        public String[] createPattern() {
            int pixelsInMatrix = matrixSize * matrixSize;
            while (dictionaryIndex < pixelsInMatrix) {
                pattern1();
                if (dictionaryIndex < pixelsInMatrix) {
                    pattern2();
                }
            }
    
            return dictionary;
        }
    
        public void pattern1() {
            for (int i = 0; i < matrixSize; i++) {
                dictionary[dictionaryIndex] = i + ":" + startY;
                dictionaryIndex++;
            }
            startY++;
        }
    
        public void pattern2() {
            for (int i = matrixSize - 1; i >= 0; i--) {
                dictionary[dictionaryIndex] = i + ":" + startY;
                dictionaryIndex++;
            }
            startY++;
        }
    }
    

    Output:

    a b c d e f
    l k j i h g
    m n o p q r
    x w v u t s
    y z 1 2 3 4
    0 9 8 7 6 5
    

    This is how the main method looks like:

    public static void main(String[] args) {
        String sentence = "abcdefghijklmnopqrstuvwxyz1234567890";
        String[][] spiral = new String[MATRIX_SIZE][MATRIX_SIZE];
    
        // Dictionary dictionary = new FrameDictionary(MATRIX_SIZE);
        Dictionary dictionary = new ClockWiseDictionary(MATRIX_SIZE);
        // Dictionary dictionary = new SnakeDictionary(MATRIX_SIZE);
    
        String[] pattern = dictionary.createPattern();
        //dictionary.showPattern();
    
        Spiral.fill(sentence, pattern, spiral);
        Spiral.show(spiral);
    }
    

    You can check/download the complete source code from GitHub.

    Hope that it helps you.

    0 讨论(0)
  • 2021-02-07 15:22

    you could try to make the spiral algorithm first and try to find the value of its each index in the matrix so that later you could map every index of your string into the specific index in the spiral array matrix.

    for example:

    Input: n = 5
    Output:   1   2   3   4   5
              16  17  18  19  6
              15  24  25  20  7
              14  23  22  21  8
              13  12  11  10  9
    Aligned Output:  1 2 3 4 5 16 17 18 19 6 15 24 25 20 7 14 23 22 21 8 13 12 11 10 9
    

    the algorithm can be found here or here.

    now you know all the index of each position to make the letters aligned in a spiral way, what you have to do is map each letter of your string to be print according to the number of the spiral matrix sequentially.

    print string 1.
    print string 2.
    print string 3.   
    print string 4.
    print string 5.
    print string 16.
    print string 17.
    print string 18.
    print string 19.
    print string 6.
    print string 15.
    cont...
    
    0 讨论(0)
  • 2021-02-07 15:23

    Here's a one with a recursive approach,

    I am traversing the matrix in right -> down -> left -> up fashion on the boundaries

    Then change the size and do the same for inner boundaries,

    Matrix M would be a spiral matrix then of character indices Create spiral matrix C for characters by traversing matrix M.

    int m = 5;
    int n = 5;
    int limit = m * n;
    int[][] M = new int[m][n];
    public void spiral(int[][] M, int row, int col, int c, int start, int m, int n) {
        if (c > limit | row >= m | col >= n)
            return;
    
        if (M[row][col] == 0)
            M[row][col] = c;
    
        if (row == start) // go right
            spiral(M, row, col + 1, c + 1, start, m, n);
    
        if (col == n - 1) // go down
            spiral(M, row + 1, col, c + 1, start, m, n);
    
        if (row == m - 1 && col > start) // go left
            spiral(M, row, col - 1, c + 1, start, m, n);
    
        if (col == start && row >= start) // go up
            spiral(M, row - 1, col, c + 1, start, m, n);
        
    };
    spiral(M, 0, 0, 1, 0, m, n);
    
    for (int i = m - 1, x = 1, j = n - 1; i >= m - 2 && j >= n - 2; i--, j--, x++)
        spiral(M, x, x, M[x][x - 1] + 1, x, i, j);
    

    This would give you spiral Matrix M Output:

    1   2   3   4   5   
    16  17  18  19  6   
    15  24  25  20  7   
    14  23  22  21  8   
    13  12  11  10  9
    

    Then create a spiral matrix for characters using matrix M

    String string = "hello_world_its_beautiful";
    char[][] C = new char[size][size];
    for (int i = 0; i < size; i++) {
        for (int j = 0; j < size; j++)
            C[i][j] = string.charAt(M[i][j] - 1);
    }
    

    Output:

    h   e   l   l   o   
    _   b   e   a   _   
    s   u   l   u   w   
    t   f   i   t   o   
    i   _   d   l   r
    
    0 讨论(0)
  • 2021-02-07 15:24

    Basically, you move through the string from start to end, but treat the stringbuffer as an array. You#ll also need to to keep track of your direction (dx,dy) and where your bounds are.

    The following code will produce:

    hello
    beau 
     l.tw
    sufio
    i dlr
    

    given the input "hello world is beautiful"

    public class Main {
    
        public static void main(String[] args) {
            String text ="hello world is beautiful";
            int len = text.length();
            double sideLength = Math.sqrt( len );
            int width = 0;
            int height = 0;
    
            // check if it's a square
            if ( sideLength > (int) sideLength) {
                // nope... it#s a rectangle
                width = (int) sideLength +1;
                height = (int) Math.ceil((double)len / (double)width);
            } else {
                // square
                width = (int) sideLength;
                height = (int) sideLength;
            }
    
            // create a buffer for the spiral
            StringBuffer buf = new StringBuffer( width * height );
            buf.setLength( width * height );
            // clear it.
            for (int a=0; a < buf.length(); a++ ) {
                buf.setCharAt(a, '.');
            }
            
    
            int dstX = 0;
            int dstY = 0;
            int curWidth =  width;
            int curHeight = height;
            int startX = 0;
            int startY = 0;
            int dx = 1;
            int dy = 0;
            // go through the string, char by char
            for (int srcPos =0; srcPos < len; srcPos++) {
                buf.setCharAt( dstX + dstY * width, text.charAt( srcPos ));
    
                // move cursor
                dstX += dx;
                dstY += dy;
    
                // check for bounds
                if ( dstX == curWidth-1 && dx > 0) {
                    // end of line while going right, need to go down
                    dx = 0;
                    dy = 1;
                    // also, reduce width
                    curWidth--;
                    startY++;
                } else if (dstY == curHeight-1 && dy > 0) {
                    // end of column while going down, need to go left
                    dx = -1;
                    dy = 0;
    
                    // also, reduce height
                    curHeight--;
                } else if (dstX == startX && dx < 0) {
                    // hit left border while going left, need to go up
                    dx = 0;
                    dy = -1;
                    // also, increase startX
                    startX++;
                } else if (dstY == startY && dy < 0) {
                    // hit top border, while going up, need to go right
                    dx = 1;
                    dy = 0;
                    // also, increase startY
                    startY++;
                }
                
            }
    
    
            // display string
            for (int line = 0; line < height; line++) {
                System.out.println( buf.substring( line* width, line*width +width) );
            }
        }
    }
    
    
    0 讨论(0)
提交回复
热议问题