Отображение среза в списке со строкой и столбцом - PullRequest
0 голосов
/ 10 июля 2019

У меня есть фрагмент с 24 словами, я хочу отобразить его с 4 строками и 6 столбцами в формате списка. Я пытаюсь реализовать это в Go.

package main

import (
    "fmt"
)

func main() {
    words := []string{"peace", "note", "vapor", "notice", "meat", "shed", "immune", "law", "web", "security", "estate", "chat", "biology", "because", "visit", "inch", "credit", "void", "ability", "police", "crush", "begin", "matrix", "wreck"}
    for i, s := range words {
        fmt.Println(i, s)
    }
}

Требуемый вывод:

1.peace      7.immune         
2.note       8.law
3.vapor      9.web
4.notice     10.security
5.meat       11.estate
6.shed       12 chat

Ответы [ 2 ]

3 голосов
/ 10 июля 2019

Вот один из способов сделать это. Вы отобразили 6 строк в необходимом выводе, однако упомянули 6 рассматриваемых столбцов. Ссылка на игровую площадку

package main

import (
    "fmt"
    "strconv"
)

func main() {
    fmt.Println("Hello, playground")
    words := [] string{"peace", "note", "vapor", "notice", "meat", "shed", "immune", "law", "web", "security", "estate", "chat", "biology", "because", "visit", "inch", "credit", "void", "ability", "police", "crush", "begin", "matrix", "wreck"}
    for i := range words {

        words[i] = strconv.Itoa(i+1) + "." + words[i]
    }
    IterSplits(SliceSplit(words, 6), 6)
}

func IterSplits(slices[][] string, splitSize int){
    for i := 0; i < splitSize; i ++ {       
        for _, s := range slices {
            if len(s) > i {
                fmt.Printf("%-15v", s[i])
            }            
        }
        println("")     
    }   
}


func SliceSplit(aSlice[] string, splitSize int) [][]string{

  var splits [][]string 

  for i := 0; i < len(aSlice); i += splitSize {
    end := i + splitSize

    if end > len(aSlice) {
        end = len(aSlice)
    }

    splits = append(splits, aSlice[i:end])
  }

  return splits
}
2 голосов
/ 10 июля 2019

Пакет fmt не имеет средств для перехода на одну строку в терминале.Есть управляющие символы, но они обычно зависят от терминала, поэтому мы должны избегать их, если сможем.

Мы можем достичь «табличного» макета, печатая элементы по строкам.Если у нас 4 строки и 6 столбцов, это означает, что первая строка будет содержать элемент 1., затем элемент 7., затем 13. и т. Д. Вторая строка будет содержать элемент 2., затем элемент 8., затемэлемент 14. и т. д.

В общем, у нас будет len(inputs) / cols рядов, округленных в большую сторону.Вот как мы можем выразить это с помощью целочисленной арифметики:

rows := (len(input) + cols - 1) / cols

И элементы в строке будут иметь индексы:

i := col*rows + row // col goes from 0 to cols

Так что в основном мы можем использовать цикл for,перебирая строки и печатая элементы строки.Мы можем использовать fmt.Printf() со строкой формата, которая содержит индекс и элемент, используя одинаковую ширину для всех элементов (выровнено по левому краю), что-то вроде этого: "%d.%-11s" (11 - это ширина дляэлементы, отрегулируйте это, если у вас есть более длинные вводимые тексты).

Индекс, однако, не всегда имеет одинаковую ширину.Например, индекс 3 имеет одну цифру, а 13 имеет 2 цифры.Таким образом, мы можем использовать «заполнение», чтобы каждый элемент и индекс занимали один и тот же индекс.Это заполнение может быть просто пробелами, и столько, сколько нужно, чтобы все индексы занимали одно и то же место.Например, если мы предположим, что у нас менее 100 элементов, то мы можем использовать 1 пробел для чисел, меньших 10, и без пробелов для чисел 10 ... 99.

Без лишних слов, вот наша простая table() функция печати, она достаточно универсальна для определения количества столбцов и позаботится об остальном:

func table(input []string, cols int) {
    rows := (len(input) + cols - 1) / cols
    for row := 0; row < rows; row++ {
        for col := 0; col < cols; col++ {
            i := col*rows + row
            if i >= len(input) {
                break // This means the last column is not "full"
            }
            padding := ""
            if i < 9 {
                padding = " "
            }
            fmt.Printf("%d.%-11s%s", i+1, input[i], padding)
        }
        fmt.Println()
    }
}

Давайте проверим это:

input := []string{
    "one", "two", "three", "four", "five", "six",
    "seven", "eight", "nine", "ten", "eleven", "twelve",
    "thirteen", "fourteen", "fifteen", "sixteen", "seventeen", "eighteen",
    "nineteen", "twenty", "twenty-one", "twenty-two", "twenty-three", "twenty-four",
}

table(input, 6)

Для вышеприведенного мы получаем следующий вывод:

1.one         5.five        9.nine        13.thirteen   17.seventeen  21.twenty-one 
2.two         6.six         10.ten        14.fourteen   18.eighteen   22.twenty-two 
3.three       7.seven       11.eleven     15.fifteen    19.nineteen   23.twenty-three
4.four        8.eight       12.twelve     16.sixteen    20.twenty     24.twenty-four

Теперь давайте проверим с 5 столбцами, где последний столбец не будет "завершен":

table(input, 5)

На этот раз вы получите:

1.one         6.six         11.eleven     16.sixteen    21.twenty-one 
2.two         7.seven       12.twelve     17.seventeen  22.twenty-two 
3.three       8.eight       13.thirteen   18.eighteen   23.twenty-three
4.four        9.nine        14.fourteen   19.nineteen   24.twenty-four
5.five        10.ten        15.fifteen    20.twenty     

Попробуйте их на Go Playground .

Note # 1:

Приведенное выше решение содержит «максимальную ширину» элементов, «подключенных».Если вы не можете сделать такое предположение, вы можете сначала перебрать элементы, чтобы получить максимальную ширину всех элементов, и использовать это в строке формата.

Вот как это можно сделать:

maxWidth := 0
for _, s := range input {
    if len(s) > maxWidth {
        maxWidth = len(s)
    }
}
format := fmt.Sprintf("%%d.%%-%ds%%s", maxWidth)

Тогда это format будет использоваться при печати элементов:

fmt.Printf(format, i+1, input[i], padding)

Попробуйте эту улучшенную версию на Go Playground .

Примечание # 2:

Также обратите внимание, что приведенный выше алгоритм может использовать меньше столбцов, чем вы передаете.Это происходит в духе «минимизации» столбцов.

Например, если длина ввода равна 24, а вы передаете cols=10, это означает, что для представления 24 элементов необходимо минимум 3 строки (только 2 строки могутотображать не более 20 элементов в 10 столбцах).Но если используются / используются 3 строки, то 24 элемента могут быть представлены всего в 8 столбцах, потому что 3 * 8 = 24.

...