brackets [,;] Конкатенация. Получатели присвоения. Результаты функции.

## Синтаксис

                Mh = [m11 m12 m13.. m1N] or [m11, m12, m13,.., m1N]
                Mv = [m11 ; m21 ; m31..; mN1]
                M  = [m11, m12,...; m21, m22,...;...]
                [r1, r2,...] = func(...)
                [r1, r2,.., rN] = (e1, e2, .., eN)
                [r1, r2,.., rk] = (e1, e2, .., ek,.., eN)
                [r1, r2,.., rN] = mylist(:)
                [r1, r2,.., rN] = S.field([i1 i2.. iN])

## Аргументы

m11, m12,...

  Множество объектов, предназначенных для конкатенации (и слияния: прежние отдельные контейнеры будут удалены). Следующие подмножества типов объектов могут смешиваться в процессе, но взаимно исключающие:

  - Матрицы логических, вещественные, комплексные значения, полиномы, дробно-рациональные значения: тип данных результата конкатенации это устанавливается правилами, определёнными ниже (см. правила преобразований типов ).
  - Матрицы кодированных целых чисел любого типа inttype.
    Кодированные целые числа различных типов не могут конкатенироваться друг с другом.
  - Cell-массивы.
  - Массивы структур с одинаковыми полями. Поля могут быть в разном порядке от одного массива к другому.
  - Типизированные списки типа syslin.
M, Mh, Mv

  Матрицы с типом всех `m##` (если они все имеют одинаковый тип данных), cell-массивы (если `mi` являются такими), массивы структур (если `mi` являются такими).

e1, e2,..

  Входные объекты (литералы, как, например, `-1.23` или `"abcd"`, переменные или выражения, как, например `a+%pi` и т.д.).

mylist

  Простой список.

S.field

  Массив структур с полем с именем `field`.

i1, i2,..

  Индексы компонентов, выбранных из `S`.

r1, r2,...

  Выходные переменные.

## Описание

[] с правой стороны: конкатенаторы

  [..] объединяют их содержимое простых и совместимых типов в единородный вектор, матрицу или гиперматрицу.

  Конкатенация по горизонтали или вертикали является двоичным итерируемым оператором. Он исполняется пошагово слева направо и сверху вниз. Таким образом, `[1 3 5 7]` исполняется как `[[[1 3] 5] 7]`.

  Внутри квадратных скобок,

  - промежутки (пробелы или табуляторы) или запятые используются в качестве разделителей столбцов.
    Использование запятых вместо пробелов безопаснее. Например, `[2 1 +%i]` означает `[2, 1, %i]`, в то время как `[2 1 + %i]` означает `[2, 1+%i]`.
  - точки с запятой или возврат каретки используются в качестве разделителей строк. Множество строк не требует точек продолжения `..`

  ### Типы преобразований

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

  1. логическое значение < кодированные целые < десятичное число < комплексное число
  2. десятичное число < полином < дробно-рациональное значение
     логические значения и полиномы не совместимы.
     - `[%t 2. %z]` допустимо: `[%t 2.]` сначала конвертируется в `[1. 2.]`, а затем принимается `[[1. 2.] %z]`.
     - `[%z %t 2.]` отклоняется и даёт ошибку. Действительно,`[%z %t]` не может конвертироваться первым.
  3. Любое кодированное целое может конкатенироваться с логическими значениями, десятичными числами или другими целыми того же типа inttype. Таким образом, выражения `[int8(2), uint8(7)]`, `[int8(2), int16(7)]`, `[int8(2), 7+0*%z]`, `[int8(2), sparse(7)]`, или `[int8(2), sparse(%t)]` приведут к ошибке.
  4. Результат становится комплексно-кодированным поскольку комплексно-кодированный компонент -- значение, полином или дробно-рациональное значение -- встречается в списке (даже с нулевой мнимой частью)

     Аналогично, результат становится разрежённо-кодированным, поскольку разрежённо-кодированный компонент встречается и обрабатывается.
  5. Можно конкатенировать полиномы или/и дробно-рациональные выражения, имеющие разные имена переменных. Затем, первый полином или дробно-рациональное выражение, встреченное в списке, устанавливает имя переменной для результата конкатенации: `[%z, 1+%s, 1-%i*%s] // => [z, 1+z, 1-iz]` .
  6. Текстовые компоненты могут конкатенироваться (в массив, ограниченный квадратными скобками) только с другим текстовыми компонентами или с пустой матрицей `[]`.

  ### Перегрузка

  - [,]: конкатенация по горизонтали: Этот оператор является двоичными и автоматически итерируется слева направо. Его код перегрузки `"c"`.
  - [;]: конкатенация по вертикали: Этот оператор является двоичными и автоматически итерируется сверху вниз. Его код перегрузки `"f"`.

  ### Расширения

  - Для конкатенации простых списков, пожалуйста, используйте lstcat.
  - Для составления векторов или матриц поверх некоторой размерности > 2 для построения N-мерного массива, пожалуйста, используйте cat.

[] на левой стороне от присвоения `"="`

  В этом случае квадратные скобки не являются конкатенаторами. Они используются в качестве левого и правого разделителя последовательностей переменных, используемых в качестве получателей.

  - Получатели должны быть переменными. Литеральные выражения не допускаются.
  - Переменные следует разделять запятыми.
  - В распределённом присвоении необходимо, чтобы получателей на левой стороне было по крайней мере столько же, сколько выходных источников, не более. Если получателей слева меньше, чем источников справа, то источники несобираемых данных игнорируется. Примеры:
    - `[a,b]=(%pi,"Hi", %z)` приемлемо, но `%z` игнорируется.
    - `[a,b,c]=(%pi,"Hi")` даст ошибку, поскольку `c` ожидает некоторой пищи.
  - `[a,b,a] = (%pi, %z, "Allo")` выполняет присвоения слева направо, таким образом, что в конце концов будет `a = "Allo"`.

## Примеры

    // Конкатенация по горизонтали
    a = [ %pi 4 -1 ]
    b1 = grand(3,4,"uin",0,10)
    b2 = grand(3,2,"uin",0,10)
    b = [b1 b2]  // они должны иметь одинаковое количество строк

    // Конкатенация по вертикали
    a = [-2 ; 10 ; 7]

    b1 = grand(2,4,"uin",0,10)
    b2 = grand(3,4,"uin",0,10)
    b = [b1 ; b2] // они должны иметь одинаковое количество столбцов

    // Смешанная конкатенация по горизонтали и вертикали
    a = [ 3 7 ; 6, 5 ]
    b = [ 1:3 ; 7:3:13]
    c = [ a b ; a b]

    d = [ 3 5
          1 4
        ]
    e = [ d d d
          d d d
        ]
    // Конкатенация данных разных типов:
    ['this is' ; 'a column' ; 'of texts']

    s = poly(0,'s');[1/s,2/s]
    [tf2ss(1/s),tf2ss(2/s)]

    [%t %f %f %T %F]

Разнородные конкатенации с автоматическими преобразованиями типов:

    [%T int8(-5)]
    [%T %pi %f 2]
    [%pi, 2+%i, %F]
    [%pi int16(-1000.84) 1.23]
    v = [%pi+0*%i, %F, %z, (1-%z)^2 ]; typeof(v), isreal(v)
    v = [10 1/%z], typeof(v)

    // Особый случай: int16 и uint8 вместе, поскольку исходное
    //   преобразование в вещественное значение распространяется слева направо
    [%pi int16(-1000.84) uint8(87)]

Несовместимые разнородные преобразования, приводящие к ОШИБКАМ:

    [%F %z]
    [int8(%pi), uint8(%e)]
    [int8(%pi), int16(%e)]
    [int8(-70), sparse(18)]
    [int8(-70), sparse([%T %F])]

Конкатенация cell-массивов:

    c1 = {%pi %t};
    c2 = {%z "abc"};
    c = [[{%i} c1] ; [c2, {1/%z^2}]]  // запятая обязательна, чтобы не считать, что c2{1/%z^2}

Распределённые присвоения:

    // Выход функции. Чаще всего, выходные результаты последовательны:
    M = rand(3,3);
    [u, s] = schur(M) // ожидаем и используем как результаты u, так и s
    u = schur(M)      // ожидаем и храним только первый результат u

    // Прямой список на правой стороне
    [a, b, c] = (%pi, %t, "test")
    [a, b] = (%e, %f, "Hello")
    [a, b, a] = (%pi, %t, "test"); a

    // Явный список на правой стороне
    L = list(%z, %i, %t, %pi, "Text");
    [a, b, c] = L(:)

    // Структура на правой стороне
    s(2,3).r = %pi; s(2,1).r = %i; s(2,2) = %e;
    s(2,:).r
    s.r([2 4 6])
    [a, b, c] = s.r([2 4 6])

    // Запрещённые / отклоняемые выражения на левой стороне (приводит к ошибке)
    [m, n, m+n] = myfun(a,b)   // Символьные выражения, такие, как "m+n" запрещены
    [p, 4.5, q] = myfun(a,b)   // Литеральные значения на левой стороне или такие выражения, как "4.5" запрещены
    [r, s+3 ] = myfun(a,b)   // Выражения, смешивающие литералы и символьные значения, такие, как "s+3" не могут быть приёмниками на левой стороне

    --> [a, b, c] = (%pi, %t, "test")
     a  =
       3.1415927

     b  =
      T

     c  =
     test

    --> [a, b] = (%e, %f, "Hello")
     a  =
       2.7182818

     b  =
      F

    --> [a, b, a] = (%pi, %t, "test"); a
     a  =
     test

## Смотрите также

- cat
- lstcat
- запятая
- точка с запятой
- фигурные скобки
- empty
- перегрузка

## История

6.0 Квадратные скобки `[..]` и фигурные скобки `{..}` теперь не эквивалентны.
6.1.0

- Логические знаения и кодированные целые числа теперь могут конкатенироваться друг с другом, как в [%t, int8(-5)].
- [a, b, ..] = (A, B,..) теперь выполняет присвоение слева направо.

6.1.1 Конкатенации между кодированными целыми и десятичными числами теперь поддерживаются.