On this page |
Обзор
VEX имеет тип массив. Это полезно в некоторых местах:
-
Поддержка параметра ramp.
-
Чтение данных с нод поверхностей с помощью функции import().
-
Общее программирование, где бы массивы ни были полезны.
Note
В настоящее время VEX не поддерживает многомерные массивы.
В этом примере показаны некоторые из сумасшедших вещей, которые вы можете делать с массивами:
surface crazy( string maps[] = { "Mandril.rat", "default.pic" }; export float alength = 0; ) { vector texclr, av[]; texclr = texture(maps[s+t > 1], s, t); av = array( {1,0,0}, vector(nrandom()), t, texclr, {.5,0,0}); if (fit(noise(s*8), 0, 1, .3, .7) > t) av = array(1, {0,1,0}, 0); Cf = spline("linear", s, av); alength = len(av); }
Объявление типов массивов
Общий вид для объявления переменной массива тип_членов имя_переменной[]
:
// my_array - это массив чисел с плавающей запятой float my_array[]; // v - это один вектор, а vector_array - это массив векторов vector v, vector_array[]; // str_array - это массив строк string str_array[];
По желанию вы можете установить размер массива внутри квадратных скобок, но компилятор VEX в настоящее время игнорирует его.
Чтобы объявить функцию, возвращающую массив:
// Функция, которая возвращает массив векторов vector[] rgb_array() { ... };
Чтобы объявить вложенную функцию, возвращающую массив:
// Функция, которая возвращает массив векторов cvex foo() { // Используйте необязательное ключевое слово «function», чтобы избежать неоднозначности типа function vector[] rgb_array() { ... }; }
Используйте фигурные скобки, чтобы указать литеральный массив, а элементы разделяйте запятыми:
vector an_array[] = { {1, 2, 3}, {2, 3, 4}, {4, 5, 6} }; vector[] rgb_array() { return { {1, 0, 0}, {0, 1, 0}, {0, 0, 1} }; }
Если вы укажете скаляр там, где ожидается вектор, компилятор автоматически присвоит данное скалярное значение всем элементам вектора:
vector an_array[] = { 1, 2, 3}; // an_array[] == { {1, 1, 1}, {2, 2, 2}, {3, 3, 3} }
Функция array()
создает массив из своих аргументов.
int my_array[] = array(1, 2, 3, 4, 5);
Вы можете использовать array()
для создания массива любого типа. Чтобы заставить array()
сгенерировать векторы, например:
vector (array (значение1, значение2, ...) );
Доступ и установка значений массива
Используйте конструкцию имямассива[индекс]
для получения значения по позиции в массиве.
vector bw[] = { 0, 1 }; // bw[] == { {0, 0, 0}, {1, 1, 1} } Cf = bw[index];
Границы массива проверяются во время выполнения. Чтение за пределами массива вернет 0
или ""
. Это может привести к возникновению предупреждения или ошибке исполнения (run-time error) в будущем. Запись за конец массива изменит размер массива, чтобы включить в него указанный индекс. Новые записи будут иметь значение 0
или ""
.
Используется индексирование в стиле языка Python. Это означает, что отрицательные индексы относятся к позициям с конца массива.
int nums[] = { 0, 1, 2, 3, 4, 5 }; int n = nums[10]; // Вернет 0 int b = nums[-2]; // Вернет 4 string strs[] = { }; string s = strs[20]; // Вернет ""
Вы также можете присваивать значения с помощью обозначения квадратных скобок.
float nums[] = { }; nums[0] = 3.14;
(Функции getcomp и setcomp являются эквивалентами для использования обозначения квадратных скобок.)
Note
Получение доступа к элементам по их позиции посредством квадратных скобок также работает для векторов. Вы также можете использовать их для матриц, используя пару скобок: float a = m3[0][1];
Срезы массивов
Квадратные скобки могут использоваться для извлечения подмассивов с использованием обозначений для срезов из языка Python.
int nums[] = { 0, 1, 2, 3, 4, 5 }; int start[] = nums[0:2]; // { 0, 1 } int end[] = nums[-2:]; // { 4, 5 } int rev[] = nums[::-1]; // { 5, 4, 3, 2, 1, 0 } int odd[] = nums[1::2]; // { 1, 3, 5 }
Функция slice является эквивалентом использования обозначения среза в квадратных скобках.
Копирование между массивами и векторами/матрицами
Оператор присваивания поддерживает возможность назначения значений массивов чисел с плавающей точкой в векторы и наоборот:
float x[]; // Cf и P векторы x = set(P); // Присваивание значений вектора P соответствующим // элементам массива x Cf = set(x); // Присваивание первых трех элементов массива x в качестве // элементов вектора Cf
Если массив не имеет достаточного количества элементов, чтобы заполнить вектор/матрицу, последний элемент повторяется столько раз, сколько необходимо для заполнения.
float x[] = {1, 2} // Недостаточно, чтобы заполнить вектор Cf = set(x); // Cf == {1, 2, 2}
Вы также можете проводить присваивание между типами матриц и массивов vector2
/vector
/vector4
:
vector2 v2[]; vector v[]; vector4 v4[]; matrix2 m2 = 1; matrix3 m3 = 1; matrix m4 = 1; v = set(m3); // Каждая строка матрицы 3x3 помещается в вектор m3 = set(v); // Копирует векторы в строки матрицы v4 = set(m4); // Извлекает строки матрицы в массив векторов (vector4) m4 = set(v4); // Создает матрицу с использованием вектора (vector4)
В итоге:
Левая сторона | = | Правая сторона | Заметки |
---|---|---|---|
vector2
|
float[]
|
Например vector2 v = {1,2}
|
|
vector
|
float[]
|
Например vector v = {1,2,3}
|
|
vector4
|
float[]
|
Например vector4 v = {1,2,3,4};
|
|
matrix2
|
float[]
|
Например matrix2 m = {1,2,3,4};
|
|
matrix2
|
vector2[]
|
Например matrix2 m = { {1,2}, {4,5} };
|
|
matrix3
|
float[]
|
Например matrix3 m = {1,2,3,4,5,6,7,8,9};
|
|
matrix3
|
vector[]
|
Например matrix3 m = { {1,2,3}, {4,5,6}, {7,8,9}};
|
|
matrix
|
float[]
|
Например matrix m = {1,2,3,4,5,6,7,8,9.., 16};
|
|
matrix
|
vector4[]
|
Например matrix m = { {1,2,3,4}, {5,6,7,8}, ... {13,14,15,16}};
|
|
float[]
|
vector2
|
Создаст массив с двумя float значениями из элементов vector2
|
|
float[]
|
vector
|
Создаст массив с тремя float значениями из элементов vector
|
|
float[]
|
vector4
|
Создаст массив с четырьмя float значениями из элементов vector4
|
|
float[]
|
matrix2
|
Создаст массив с четырьмя float значениями из элементов matrix2
|
|
vector2[]
|
matrix2
|
Создаст массив с двумя vector2 значениями из элементов matrix2
|
|
float[]
|
matrix3
|
Создаст массив с девятью float значениями из элементов matrix3
|
|
vector[]
|
matrix3
|
Создаст массив с тремя vector значениями из элементов matrix3
|
|
float[]
|
matrix4
|
Создаст массив с шестнадцатью float значениями
|
|
vector4[]
|
matrix4
|
Создаст массив с четырьмя vector4 .
|
Перебор элементов массива
Смотрите foreach.
Работа с массивами
Следующие функции позволят вам всячески манипулировать массивами.
Устанавливает длину массива. Если массив был увеличен, промежуточные значения будут заполнены 0
или ""
.
Возвращает длину массива.
Удаляет последний элемент из массива (уменьшая размер массива на 1) и возвращает удаленный элемент.
Добавляет элемент в конец массива (увеличивая размер массива на 1).
Возвращает значение компонента массива, то же, что array[num]
.
Устанавливает значение компонента массива, то же, что и array[num] = value
.
Эффективно создает массив из своих аргументов.
Превращает массив векторов или матриц в массив float
значений.
Обращает эффект serialize: собирает плоский массив float
значений в массив векторов или матриц.
Основанная на массиве замена комбинации neighbourcount/neighbour. Возвращает массив номеров точек соседних с данной точкой.
Следующие функции также работают с массивами:
Псевдокомментарии компилятора VCC (Pragmas)
Псевдокомментарий ramp
позволяет указать пользовательский интерфейс "ramp" для набора параметров.
#pragma ramp <ramp_parm> <basis_parm> <keys_parm> <values_parm>
Смотрите псевдокомментарии компилятора VCC для получения дополнительной информации.
Ограничения
-
В настоящее время VEX не поддерживает многомерные массивы.
-
Массивы не могут передаваться между шейдерами (через simport, и т.д.).
-
Массивы не могут быть записаны в изображения.