-
Notifications
You must be signed in to change notification settings - Fork 53
Problem in map_into_symmetry_reduced_zone #368
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
@maclariz could you provide the original orientation data before calling |
@harripj Here you go: [ 0.5101 -0.0107 0.0421 -0.859 ]
[ 0.5114 -0.0107 0.0421 -0.8582]
[ 0.2451 -0.0222 0.0373 -0.9685]
[ 0.2455 -0.016 0.0368 -0.9686]
[ 0.2442 -0.0223 0.0373 -0.9688] |
@harripj m3m (FCC) |
The following sorted out my data and resulted in a consistent set of orientations that give consistent misorientation angles: # Take the data into a pure numpy array
ori5 = ori3.data
# Drop into a setting where index 0 (cos angle) is positive, 1 (prop to x) and 2 (prop to y) are negative
# and index 3 (prop to z) are positive
ori5[:,0] = abs(ori5[:,0])
ori5[:,1] = -abs(ori5[:,1])
ori5[:,2] = -abs(ori5[:,2])
ori5[:,3] = abs(ori5[:,3])
# Transform back into orientation object without calling symmetry
ori5 = Orientation(ori5)
ori5
# Make a new mean orientation object without symmetry
mean4_1 = all4.mean()
mean4_1
# Make new misorientation object
ori6 = ori5-mean4_1 this is in no way a general solution, but works on a dataset where all orientations are broadly similar and map into a set of distinct orientation in a roughly 30 degree range (except for the odd noisy misindexed point). |
Hi @maclariz, I just eyeballed this in my lunchtime, but I think the sign flips might just be part of how fundamental zones worked. I would be interested to know what happens if you use orix/orix/quaternion/orientation.py Line 383 in 2d18672
|
@pc494 I don't know what this really adds, but I'll give you some output from this. This is a distance matrix of 6 points in this area with the orientation flips, converted to degrees (with np.degrees): array([[ 0. , 33.23155212, 0.05729578, 33.2888479 , 0.72280107,0.05729578],
[33.23155212, 0. , 33.17425634, 0.05729578, 33.1164664 ,33.2888479 ],
[ 0.05729578, 33.17425634, 0. , 33.23155212, 0.71532024, 0.11459156],
[33.2888479 , 0.05729578, 33.23155212, 0. , 33.17374857, 33.34614368],
[ 0.72280107, 33.1164664 , 0.71532024, 33.17374857, 0. , 0.73468719],
[ 0.05729578, 33.2888479 , 0.11459156, 33.34614368, 0.73468719,0. ]]) It would seem there are some different orientations there with very small angles above the lowest, and it is probably flipping between different solutions, purely on metric of lowest angle, rather than sticking with a consistent orientation of the x,y,z axes of the cell... |
@pc494 Here is the result of .to_matrix() on the same 6 data points: array([[[ 0.87929659, -0.4723087 , -0.06133516],
[ 0.47562573, 0.8775068 , 0.06133494],
[ 0.024853 , -0.08310418, 0.99623091]],
[[ 0.87873789, 0.47334738, 0.06133494],
[-0.47666228, 0.87694416, 0.06133516],
[-0.02475448, -0.08313358, 0.99623091]],
[[ 0.87882384, -0.47318776, -0.06133516],
[ 0.476503 , 0.87703074, 0.06133494],
[ 0.02476988, -0.08312899, 0.99623091]],
[[ 0.8792108 , 0.47246841, 0.06133494],
[-0.4757851 , 0.87742039, 0.06133516],
[-0.0248376 , -0.08310878, 0.99623091]],
[[ 0.87893279, -0.47441358, -0.04908061],
[ 0.47676917, 0.87674227, 0.0633573 ],
[ 0.01297348, -0.07908693, 0.9967833 ]],
[[ 0.87976846, -0.47142916, -0.06133516],
[ 0.47474799, 0.87798199, 0.06133494],
[ 0.02493609, -0.08307929, 0.99623091]]]) It is simply arbitrary sign flips on axes that is messing this up. |
So if I run: o = Orientation([[ 0.5101, -0.0107, 0.0421, -0.859 ],
[ 0.5114, -0.0107, 0.0421, -0.8582],
[ 0.2451, -0.0222, 0.0373, -0.9685],
[ 0.2455, -0.016 , 0.0368, -0.9686],
[ 0.2442, -0.0223, 0.0373, -0.9688]], symmetry=Oh)
# distance matrix original data
d1 =o.get_distance_matrix()
# distance matrix symmetry reduced data
o2 = o.map_into_symmetry_reduced_zone()
d2 = o2.get_distance_matrix()
# compute fractional error
diff = (d2 - d1) / d1
diff[np.diag_indices(diff.shape[0])] = 0
np.abs(diff.max())
0.0175 which tells me there is <2% error between @maclariz I get different results on my machine, which we should clarify before going forward: >>> o
Orientation (5,) m-3m
[[ 0.5101 -0.0107 0.0421 -0.859 ]
[ 0.5114 -0.0107 0.0421 -0.8582]
[ 0.2451 -0.0222 0.0373 -0.9685]
[ 0.2455 -0.016 0.0368 -0.9686]
[ 0.2442 -0.0223 0.0373 -0.9688]]
>>> o2
Orientation (5,) m-3m
[[ 0.9681 0.0222 0.0373 -0.2467]
[ 0.9685 0.0222 0.0373 -0.2452]
[ 0.9685 0.0373 0.0222 0.2451]
[ 0.9686 0.0368 0.016 0.2455]
[ 0.9688 0.0373 0.0223 0.2442]] |
I've changed the order of which symmetry elements are applied to the left and right of (mis)orientations when reducing them to the fundamental zone in #442. After this change, I get the following result import numpy as np
from orix.quaternion import Orientation, symmetry
o = Orientation([[ 0.5101, -0.0107, 0.0421, -0.859 ],
[ 0.5114, -0.0107, 0.0421, -0.8582],
[ 0.2451, -0.0222, 0.0373, -0.9685],
[ 0.2455, -0.016 , 0.0368, -0.9686],
[ 0.2442, -0.0223, 0.0373, -0.9688]], symmetry=symmetry.Oh)
# distance matrix original data
d1 = o.get_distance_matrix()
# distance matrix symmetry reduced data
o2 = o.reduce() # Replaces map_into_symmetry_reduced_zone()
print(o2)
# Orientation (5,) m-3m
# [[ 0.9681 -0.0373 0.0222 -0.2467]
# [ 0.9685 -0.0373 0.0222 -0.2452]
# [ 0.9685 -0.0373 -0.0222 0.2451]
# [ 0.9686 -0.0368 -0.016 0.2455]
# [ 0.9688 -0.0373 -0.0223 0.2442]]
d2 = o2.get_distance_matrix()
np.allclose(d1, d2)
# True @maclariz, @harripj, I would be very happy if you could check out the branch in #442 and try |
Hey, I'm super late to this party, but I believe ORIX was behaving correctly from the start. @maclariz , your orientations are vaguely close together, but they still fall into different symmetry reduction zones. As such, orix correctly gave you the symmetry-reduced representations, they just look incorrect because they map to opposite sides of the m3m FZ. Code for proof:
Which shows the first two elements use symmetry element 1 (a 4-fold over the 001) while the last 3 use symmetry element 2 ( a 2-fold over the 001). Importantly, these look EXACTLY alike on an IPF plot. This is also why @harripj saw a 2% difference between o1 and o2 as well, as they are physically different orientations. they represent twists of slightly different angular intensity around the same axis. @hakonanes, I think #442 is irrelevant to this specific case, but it fixes the extension of this problem to Misorientation space. (ie, enforcing agreement with the Krakow paper for consistent handling of misorientation FZs: https://royalsocietypublishing.org/doi/10.1098/rspa.2017.0274 ) As another proof, you can calculate the distances between every element. the original rotations give:
and Orix's symmetry-reduced orientatoins give:
which is the same, but the alternate rotations given in the first comment as "equivalent" give different angular distances, which cannot be arrived at by any combination of symmetry operations.
This is a bit of an assumption, but if I had to guess, this is linked to the practice in plotting certain vector maps (XRD, IPF maps, and TEM diffraction patterns) where reordering the scalar part of a quaternion is a quick and easy way to reduce it to the fundamental zone of the IPF plot. However, the sign swap done in the first comment does not represent an identical rotation, only a rotation that has identical magnitude and maps to the same xy position in a stereographic projection. The consequences of this are really easy to miss as well since the difference rarely matters (until it does), they have the same disorientation angle, they map the same way in nearly all non-3D plots, and they are equivalent for most diffraction-based calculations. Thus, most checks based on vector analysis would still treat them as equivalent. The plot below is a map of the FZ, with blue dots representing the correct values for the orientations, and the orange spots are the improper remapping. @maclariz , My (possibly incorrect) assumption, given how close the orange dots are to the blue, is before you got to orix, some previous code flipped the signs and/or ordering on your rotations for convenience, or only gave one of the 3 possible rotations that could have mapped a 100 Miller index to an observed spot in a diffraction experiment. If the second, this could be described by a different and/or incorrect handling of symmetry operations in the prior software. If anyone disagrees, feel free to refute this, but my understanding is ORIX did what it was supposed to in this case. |
Running map_into_symmetry_reduced_zone() on sensible data (single crystal, all similar orientations) yields the following (just a few lines shown for illustration):
Fixing this manually in a quick for loop gets me to:
(which is just a numpy array)
reimporting as an Orientation object, it then just transforms back to the first. Obviously, the constant sign flips in this data on index 2 and 3 in each quaternion play merry hell with any calculations!
The text was updated successfully, but these errors were encountered: