#rotation #julia #affinetransform
#поворот #julia #аффинетрансформирует
Вопрос:
Я использую AffineTransforms для поворота тома. Теперь меня смущает знак угла поворота. Для правой системы при взгляде вниз на ось, скажем, ось Z, поворот плоскости XY против часовой стрелки должен составлять положительные углы. Я определяю матрицу вращения r = [0.0 -1. 0.0; 1.0 0.0 0.0; 0.0 0.0 1.0]
, которая должна вращаться вдоль оси Z на 90 градусов против часовой стрелки. Действительно, r * [1 0 0]'
дает [ 0 1 0]'
, который поворачивает ось X на ось Y.
Теперь я определяю объем v.
3×3×3 Array{Float64,3}:
[:, :, 1] =
0.0 0.0 0.0
0.0 0.0 0.0
0.0 0.0 0.0
[:, :, 2] =
0.0 0.0 0.0
1.0 0.0 0.0
0.0 0.0 0.0
[:, :, 3] =
0.0 0.0 0.0
0.0 0.0 0.0
0.0 0.0 0.0
затем я определяю tfm = AffineTransform(r, vec([0 0 0])))
, что совпадает с tfm = tformrotate(vec([0 0 1]), π/2)
.
затем transform(v, tfm)
. Центр поворота — это центр входного массива. Я получил
3×3×3 Array{Float64,3}:
[:, :, 1] =
0.0 0.0 0.0
0.0 0.0 0.0
0.0 0.0 0.0
[:, :, 2] =
0.0 1.0 0.0
0.0 0.0 0.0
0.0 0.0 0.0
[:, :, 3] =
0.0 0.0 0.0
0.0 0.0 0.0
0.0 0.0 0.0
Это удивительно для меня, потому что результатом является поворот на 90 градусов вдоль оси Z, но по часовой стрелке. Мне кажется, что на самом деле это поворот на -90 градусов. Может кто-нибудь указать, что я сделал не так? Спасибо.
Ответ №1:
По общему признанию, это меня тоже смутило. Пришлось transform
снова и TransformedArray
снова читать справку.
Во-первых, порядок печати массивов немного сбивает с толку, так как первый индекс отображается в столбцах, но это ось X, так как размеры v
x,y,z
указаны в этом порядке.
В оригинале v
мы имеем v[2,1,2] == 1.0
. Но по умолчанию transform
в качестве начала координат используется центр массива, поэтому 2,1,2
он относится к центру (0,-1,0), т.Е. единичный вектор в отрицательном направлении оси y.
Массив, возвращаемый с помощью transform
, имеет значения, которые оцениваются x,y,z
путем присвоения значения исходного v
значения at tfm((x,y,z))
(см. ?TransformedArray
).
В частности, у нас есть transform(v,tfm)[1,2,2]
is v[tfm((-1,0,0))]
, который равен v[(0,-1,0)]
(потому что вращение (-1,0,0) против часовой стрелки равно (0,-1,0)), который находится v[2,1,2]
в нецентрированных v
индексах. Наконец, v[2,1,2] == 1.0
как и в выходных данных в вопросе.
Преобразование координат всегда сложно, и легко спутать преобразования и их обратные.
Надеюсь, это поможет.
Комментарии:
1. Спасибо! @dan-getz. Прочитав ваш ответ, я вернулся к чтению справки
transform
иTransformedArray
также.2. Таким
transform
образом, фактически возвращается массив, который находится перед поворотом. Это обратное преобразование. Чтобы получить объем после поворота или любого преобразования, мне нужно использовать обратное преобразование. Это правильно?3.
transform
в основном принимает стандартные координаты точек в объеме (в данном случае 1: 3 x 1: 3 x 1: 3), применяетtfm
к ним и просматриваетv
результат. Таким образом, вы получаете матрицу того же размера, но кtfm
результату применяется преобразование, поэтому, чтобы применить преобразование к источнику, вам нужно использовать обратное.