我们如何向左旋转数组?
How can we rotate an array to the left?
EX:我有一个数组 {1, 2, 3, 4, 5}
和一个整数 7
它会向右旋转 7
个空格,例如:{4, 5, 1, 2, 3}
我还有那个数组 {1, 2, 3, 4, 5}
和一个整数 -7
它会向左旋转 7
个空格,例如:{3, 4, 5, 1, 2}
我使用以下方法将数组向右旋转:
for(int i = 0; i < data.length; i++){
result[(i+n) % data.length ] = data[i];
}
但是我们如何向左旋转数组呢?
向左旋转n等同于向右旋转长度-n。
向右旋转(对于正 n):
for(int i = 0; i < data.length; i++){
result[(i+n) % data.length ] = data[i];
}
向左旋转(对于正 n):
for(int i = 0; i < data.length; i++){
result[(i+(data.length-n)) % data.length ] = data[i];
}
这样就可以避免对负数取模。
如果你想输入一个整数n,如果n为正则向右旋转,如果n为负则向左旋转,你可以这样做:
int[] rotateArray(int n, int[] data)
{
if(n < 0) // rotating left?
{
n = -n % data.length; // convert to +ve number specifying how
// many positions left to rotate & mod
n = data.length - n; // rotate left by n = rotate right by length - n
}
int[] result = new int[data.length];
for(int i = 0; i < data.length; i++){
result[(i+n) % data.length ] = data[i];
}
return result;
}
如果向左旋转,您可以使用它来避免对负数取模:
int[] data = {1, 2, 3, 4, 5};
int[] result = new int[data.length];
for (int i = 0; i < data.length; i++) {
result[(i + (data.length - 2)) % data.length] = data[i];
}
for (int i : result) {
System.out.println(i);
}
您也可以使用链表来实现相同的目的。
Integer[] arr = {1,2,3,4,5};
LinkedList<Integer> ns = new LinkedList<Integer>(Arrays.asList(arr));
int rotate=3;
if(rotate<0)
rotate += arr.length;
List<Integer> leftlist = ns.subList(0, rotate);
List<Integer> rightlist = ns.subList(rotate, arr.length);
LinkedList<Integer> result = new LinkedList<Integer>();
result.addAll(rightlist);
result.addAll(leftlist);
System.out.println(result);
这是完整的 java 数组左旋转 n 次的程序。
public class ArrayRotation {
private static Scanner sc;
public static void main(String[] args) {
int n,k;
sc = new Scanner(System.in);
System.out.print("Enter the size of array: ");
n = sc.nextInt();
int[] a = new int[n];
System.out.print("Enter the "+n+" elements in the list: ");
for(int i=0;i<n;i++)
a[i] = sc.nextInt();
System.out.print("Enter the number of left shifts to array: ");
k = sc.nextInt();
System.out.print("Array before "+k+" shifts: ");
display(a);
solution(a,k);
System.out.println();
System.out.print("Array after "+k+" shifts: ");
display(a);
}
public static void solution(int[] a, int k){
int temp=0, j;
for(int i=0;i<k;i++){
temp = a[0];
// j=0; // both codes work i.e. for loop and while loop as well
// while(j<a.length-1){
// a[j]=a[j+1];
// j++;
// }
for(j=0;j<a.length-1;j++)
a[j]=a[j+1];
a[j]=temp;
}
}
public static void display(int[] a){
for(int i=0;i<a.length;i++)
System.out.print(a[i]+" ");
}
}
public static int[] arrayLeftRotation(int[] array, int elements, int rotations) {
// i = checks number of rotations
for (int i = 0; i < rotations; i++) {
int first = array[0];
int last = array[elements - 1];
// j = rotates each element
for (int j = 0; j < elements; j++) {
// check if at first index
if (j == 0) {
array[elements - 1] = first;
}
// check if at last index
if (j == (elements - 1)) {
// if at last index: make element in index before last = to last element
array[elements - 2] = last;
} else {
array[j] = array[j + 1];
}
}
}
return array;
}
这是我能想到的最清晰的答案。
请注意,您需要计算 rotations % length
以便您的程序对大于数组大小的旋转次数具有鲁棒性。
static int[] rotateLeft(int[] arr, int rotations) {
int length = arr.length;
int[] result = new int[length];
rotations = rotations % length; // robust to rotations > length
int position = length - rotations; // compute outside the loop to increase performance
for (int i = 0; i < length; i++) {
result[(position + i) % length] = arr[i];
}
return result;
}
如果你想旋转一个名为 a[n]
的数组,n
作为数组的大小,d
作为旋转的次数(在你的例子中 d=7
), 你可以使用这个代码:
d = d % n;
for(int i=d;i<n;i++){
System.out.print(a[i]+" ");
}
for(int i=0;i<(d);i++){
System.out.print(a[i]+" ");
}
这段代码会在执行左旋转后按顺序打印数组元素。如果你愿意,你可以将它存储在另一个数组中,或者你可以按照上面的方法显示数组元素。
我使用以下方法将数组放入新位置的新数组中。
int length = a.length;
int[] newArr = new int[a.length];
for (int i = length - 1; i >= 0 ; i--){
int newPosition = i - d; // d is the number of rotation
if (newPosition < 0)
newPosition = length + newPosition;
newArr[newPosition] = a[i];
}
最初我想使用下面的方法交换到同一个数组,但它并不适用于所有情况。例如,由于旋转而交换了 2 个数组元素。所以 newPosition 和 position 继续指向对方。因此数组的其余部分不会移动。
不确定是否可以在同一数组中以 O(n) 复杂度旋转数组。
int length = a.length;
int position = length-1;
int temp = a[position];
for (int i = 0; i < length; i++){
int newPosition = position - d;
if (newPosition < 0)
newPosition = length + newPosition;
int cache = a[newPosition];
a[newPosition]= temp;
temp = cache;
position = newPosition;
}
这是我在 Javascript 中的解决方案:
n 是元素数,r 是旋转数。
a 是数组。
function rotate(a,r,n)}
for(var i = 0; i<r; i++){
var aa = array[0] //
for (var j = 0; j < n-1; j++){
array[j] = array[j+1] //
}
array[n-1] = aa //
}
return a
}
var array = [1,2,3,4,5];
console.log(rotate(array,1,5))
// Left rotation using lambda expression.
int [] ar = {1,6,7,5,9,1,34,7};
int shift =2;
int[] posAr = IntStream.range(0, ar.length).map(i->(ar[(i + (ar.length + shift)) % ar.length])).toArray();
//You can print the data
Arrays.stream(posAr).forEach(System.out::println);
enter image description here
显示代码:
if(a.length==0 || a.length==1)
return a;
int r=d%a.length;
int A[]=new int[a.length];
for (int i = 0; i < a.length; i++) {
if((i+r) >= a.length)
A[i]=a[i+r-a.length];
else
A[i]=a[i+r];
}
return A;
EX:我有一个数组 {1, 2, 3, 4, 5}
和一个整数 7
它会向右旋转 7
个空格,例如:{4, 5, 1, 2, 3}
我还有那个数组 {1, 2, 3, 4, 5}
和一个整数 -7
它会向左旋转 7
个空格,例如:{3, 4, 5, 1, 2}
我使用以下方法将数组向右旋转:
for(int i = 0; i < data.length; i++){
result[(i+n) % data.length ] = data[i];
}
但是我们如何向左旋转数组呢?
向左旋转n等同于向右旋转长度-n。
向右旋转(对于正 n):
for(int i = 0; i < data.length; i++){
result[(i+n) % data.length ] = data[i];
}
向左旋转(对于正 n):
for(int i = 0; i < data.length; i++){
result[(i+(data.length-n)) % data.length ] = data[i];
}
这样就可以避免对负数取模。
如果你想输入一个整数n,如果n为正则向右旋转,如果n为负则向左旋转,你可以这样做:
int[] rotateArray(int n, int[] data)
{
if(n < 0) // rotating left?
{
n = -n % data.length; // convert to +ve number specifying how
// many positions left to rotate & mod
n = data.length - n; // rotate left by n = rotate right by length - n
}
int[] result = new int[data.length];
for(int i = 0; i < data.length; i++){
result[(i+n) % data.length ] = data[i];
}
return result;
}
如果向左旋转,您可以使用它来避免对负数取模:
int[] data = {1, 2, 3, 4, 5};
int[] result = new int[data.length];
for (int i = 0; i < data.length; i++) {
result[(i + (data.length - 2)) % data.length] = data[i];
}
for (int i : result) {
System.out.println(i);
}
您也可以使用链表来实现相同的目的。
Integer[] arr = {1,2,3,4,5};
LinkedList<Integer> ns = new LinkedList<Integer>(Arrays.asList(arr));
int rotate=3;
if(rotate<0)
rotate += arr.length;
List<Integer> leftlist = ns.subList(0, rotate);
List<Integer> rightlist = ns.subList(rotate, arr.length);
LinkedList<Integer> result = new LinkedList<Integer>();
result.addAll(rightlist);
result.addAll(leftlist);
System.out.println(result);
这是完整的 java 数组左旋转 n 次的程序。
public class ArrayRotation {
private static Scanner sc;
public static void main(String[] args) {
int n,k;
sc = new Scanner(System.in);
System.out.print("Enter the size of array: ");
n = sc.nextInt();
int[] a = new int[n];
System.out.print("Enter the "+n+" elements in the list: ");
for(int i=0;i<n;i++)
a[i] = sc.nextInt();
System.out.print("Enter the number of left shifts to array: ");
k = sc.nextInt();
System.out.print("Array before "+k+" shifts: ");
display(a);
solution(a,k);
System.out.println();
System.out.print("Array after "+k+" shifts: ");
display(a);
}
public static void solution(int[] a, int k){
int temp=0, j;
for(int i=0;i<k;i++){
temp = a[0];
// j=0; // both codes work i.e. for loop and while loop as well
// while(j<a.length-1){
// a[j]=a[j+1];
// j++;
// }
for(j=0;j<a.length-1;j++)
a[j]=a[j+1];
a[j]=temp;
}
}
public static void display(int[] a){
for(int i=0;i<a.length;i++)
System.out.print(a[i]+" ");
}
}
public static int[] arrayLeftRotation(int[] array, int elements, int rotations) {
// i = checks number of rotations
for (int i = 0; i < rotations; i++) {
int first = array[0];
int last = array[elements - 1];
// j = rotates each element
for (int j = 0; j < elements; j++) {
// check if at first index
if (j == 0) {
array[elements - 1] = first;
}
// check if at last index
if (j == (elements - 1)) {
// if at last index: make element in index before last = to last element
array[elements - 2] = last;
} else {
array[j] = array[j + 1];
}
}
}
return array;
}
这是我能想到的最清晰的答案。
请注意,您需要计算 rotations % length
以便您的程序对大于数组大小的旋转次数具有鲁棒性。
static int[] rotateLeft(int[] arr, int rotations) {
int length = arr.length;
int[] result = new int[length];
rotations = rotations % length; // robust to rotations > length
int position = length - rotations; // compute outside the loop to increase performance
for (int i = 0; i < length; i++) {
result[(position + i) % length] = arr[i];
}
return result;
}
如果你想旋转一个名为 a[n]
的数组,n
作为数组的大小,d
作为旋转的次数(在你的例子中 d=7
), 你可以使用这个代码:
d = d % n;
for(int i=d;i<n;i++){
System.out.print(a[i]+" ");
}
for(int i=0;i<(d);i++){
System.out.print(a[i]+" ");
}
这段代码会在执行左旋转后按顺序打印数组元素。如果你愿意,你可以将它存储在另一个数组中,或者你可以按照上面的方法显示数组元素。
我使用以下方法将数组放入新位置的新数组中。
int length = a.length;
int[] newArr = new int[a.length];
for (int i = length - 1; i >= 0 ; i--){
int newPosition = i - d; // d is the number of rotation
if (newPosition < 0)
newPosition = length + newPosition;
newArr[newPosition] = a[i];
}
最初我想使用下面的方法交换到同一个数组,但它并不适用于所有情况。例如,由于旋转而交换了 2 个数组元素。所以 newPosition 和 position 继续指向对方。因此数组的其余部分不会移动。 不确定是否可以在同一数组中以 O(n) 复杂度旋转数组。
int length = a.length;
int position = length-1;
int temp = a[position];
for (int i = 0; i < length; i++){
int newPosition = position - d;
if (newPosition < 0)
newPosition = length + newPosition;
int cache = a[newPosition];
a[newPosition]= temp;
temp = cache;
position = newPosition;
}
这是我在 Javascript 中的解决方案: n 是元素数,r 是旋转数。 a 是数组。
function rotate(a,r,n)}
for(var i = 0; i<r; i++){
var aa = array[0] //
for (var j = 0; j < n-1; j++){
array[j] = array[j+1] //
}
array[n-1] = aa //
}
return a
}
var array = [1,2,3,4,5];
console.log(rotate(array,1,5))
// Left rotation using lambda expression.
int [] ar = {1,6,7,5,9,1,34,7};
int shift =2;
int[] posAr = IntStream.range(0, ar.length).map(i->(ar[(i + (ar.length + shift)) % ar.length])).toArray();
//You can print the data
Arrays.stream(posAr).forEach(System.out::println);
enter image description here
显示代码:
if(a.length==0 || a.length==1)
return a;
int r=d%a.length;
int A[]=new int[a.length];
for (int i = 0; i < a.length; i++) {
if((i+r) >= a.length)
A[i]=a[i+r-a.length];
else
A[i]=a[i+r];
}
return A;