java - Is an XOR swap equivalent to a traditional swap in all cases? -
below method performs ‘in place ' string reverse i.e. black cat becomes cat black. in second swap section if traditional swap (commented out) used tests pass if xor swap used 1 test passes.
is not possible 'swap'
(int = count; <= (end + count) / 2; i++) { char temp = arr[i]; arr[i] = arr[end - (i - count)]; arr[end - (i - count)] = temp; }
to
(int = count; <= (end + count) / 2; i++) { arr[i] ^= arr[end - (i - count)]; arr[end - (i - count)] ^= arr[i]; arr[i] ^= arr[end - (i - count)]; }
method
public class reversestring { public static char[] revstring(string input) { char[] arr = input.tochararray(); int length = arr.length; (int = 0; < (length / 2); i++) { arr[i] ^= arr[length - - 1]; arr[length - - 1] ^= arr[i]; arr[i] ^= arr[length - - 1]; } int end; int charcount; int count = 0; while (count < length) { if (arr[count] != ' ') { charcount = 0; while (count + charcount < length && arr[count + charcount] != ' ') { charcount++; } end = count + charcount - 1; // (int = count; <= (end + count) / 2; i++) { // char temp = arr[i]; // arr[i] = arr[end - (i - count)]; // arr[end - (i - count)] = temp; // } (int = count; <= (end + count) / 2; i++) { arr[i] ^= arr[end - (i - count)]; arr[end - (i - count)] ^= arr[i]; arr[i] ^= arr[end - (i - count)]; } count += charcount; } else { count++; } } return arr; } }
test
@runwith(junitparamsrunner.class) public class reversestringtest { @test @parameters(method = "getstrings") public void testrevstring(string testvalue, char[] expectedvalue) { assertthat(reversestring.revstring(testvalue), equalto(expectedvalue)); } private static final object[] getstrings() { return new object[] { new object[] {"black cat", "cat black".tochararray()}, new object[] {"left to", "to left".tochararray()} }; } }
output fail
java.lang.assertionerror: expected: ["c", "a", "t", " ", "b", "l", "a", "c", "k"] but: ["c", "
xor swap fails when swapping value itself. here's code:
arr[i] ^= arr[end - (i - count)]; arr[end - (i - count)] ^= arr[i]; arr[i] ^= arr[end - (i - count)];
let's assume i == end - (i - count)
. then:
arr[i] ^= arr[end - (i - count)];
sets arr[i]
0 (since xor'd zero).
the next 2 lines nothing, xor'ing 0 has no effect, leaving arr[i]
0 , corrupting input.
whether above assumption ever true depends on length of input, noted.
because of gotcha, xor swapping dangerous. since it's hard read, , isn't performance win on modern platform, micro-optimization trick obsolete , should avoided.
Comments
Post a Comment