I am trying to write a function which iterates through an array and when it finds a certain type of value it will shift it to the right a defined number of places.
I know how to shift elements by temporarily storing a value, shifting the right side elements to the left and then writing the temporary value in the correct place.
The bit I am struggling with is if the certain character appears near the end of the array I need it to wrap around and continue from the start of the array, so is circular.
So an array shifting, for example, capital letters to the right 3 places and special characters to the left 1 place:
{ M, y, N, a, m, e, P} becomes...
{ y, M, P, a, N, m, e}
To shift an element of 8 to the right 3 places I have below, but this only works if 8 appears earlier than 3 elements from the end of the array and will not wrap around.
input array:
{0, 1, 2, 3, 4, 5, 6, 7, **8**, 9}
desired output:
{0, **8**, 1, 2, 3, 4, 5, 6, 7, 9}
int[] array = new int[]{0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
for (int i = array.Length - 1; i >= 0; i--)
{
if (array[i] == 8)
{
int temp = array[i];
int j = 0;
for (j = i; j < i + 3; j++)
{
array[j] = array[j + 1];
}
array[j] = temp;
}
}
Just use modulo arithmetic so that instead of writing to the element at index j
as you shift, instead write to the element at index j % array.Length
. Thusly:
public void FindAndShift<T>(T[] array, T value, int shift) {
int index = Array.IndexOf(array, value);
int shiftsRemaining = shift;
for(int currentPosition = index; shiftsRemaining > 0; shiftsRemaining--) {
array[currentPosition % array.Length] = array[(currentPosition + 1) % array.Length];
}
array[(index + shift) % array.Length] = value;
}
I have excluded error checking.