Преобразуйте индекс 2D массива в индекс 1D

#java #arrays #matrix #multidimensional-array #simd

#Ява #массивы

Вопрос:

У меня есть два массива для шахматного варианта, который я кодирую на java…До сих пор у меня есть консольная версия, которая представляет плату в виде массива 1D (размер 32), но я работаю над созданием графического интерфейса для нее и хочу, чтобы он отображался в виде сетки 4×8, поэтому у меня есть 2-мерный массив JPanels…

Вопрос в том, существует ли какая-либо формула, которая может преобразовать индекс массива[i][j] в массив[i], учитывая тот факт, что он представляет собой массив 4×8?

Ответ №1:

Подумайте об этом так:

У вас есть один массив, который является 1-мерным массивом, который на самом деле представляет собой просто длинное объединение элементов двумерного массива.

Итак, предположим, у вас есть двумерный массив размером 5 х 3 (5 строк, 3 столбца). И мы хотим создать одномерный массив. Вам нужно решить, хотите ли вы объединяться по строкам или по столбцам, в этом примере мы скажем, что объединение выполняется по строкам. Таким образом, каждая строка имеет длину 3 столбца, поэтому вам нужно думать, что ваш одномерный массив определен в «шагах» из 3. Таким образом, длина вашего одномерного массива будет 5 х 3 = 15, и теперь вам нужно найти точки доступа.

Итак, предположим, что вы обращаетесь ко 2-й строке и 2-му столбцу вашего двумерного массива, тогда это будет 3 шага (первая строка) количество шагов во второй строке или 3 2 = 5. Поскольку мы индексируем на основе нуля, это -1, так что это будет индекс 4.

Теперь перейдем к конкретной формулировке:

 int oneDindex = (row * length_of_row)   column; // Indexes  

Итак, в качестве примера вышесказанного вы могли бы получить

 oneDindex = (1 * 3)   1  

И это должно быть так

Комментарии:

1. Отлично! Большое спасибо за объяснение того, как добраться до формулы!

2. @Michael это было отличное объяснение и даже 1 u, но не могли бы вы уточнить: «Итак, допустим, вы обращаетесь ко 2-й строке и 2-му столбцу вашего двумерного массива, тогда это будет 3 шага (первая строка) количество шагов во второй строке или 3 2 = 5. Поскольку мы индексируем на основе нуля, это -1, так что это будет индекс 4». лучше. объясни это получше.

Ответ №2:

Дано 4 столбца по 8 строк, затем:

 i = row * 4   col  

ПРАВКА: Моя ошибка, очевидно, никто не поймал меня на этой ошибке. Но на самом деле так и должно быть row * 4 col .

row * 8 col это оставило бы ненужные пробелы в возможных индексах.

Комментарии:

1. Я не могу поверить, что я не понял этого лол… У меня было (i*4) (i*8) неудивительно, что это было за пределами, спасибо!

2. Всегда пожалуйста. Недавно мне пришлось проделать то же самое с обучающей игрой в крестики-нолики. Хранение прошлых ходов в виде единого индекса стало шагом на пути к повышению эффективности.

3. Я всегда возвращаюсь к этому ответу, по какой-то причине я просто не могу найти способ запомнить это уравнение index = x y * num_cols; , было бы неплохо добавить, как мы его выводим!

4. Просто и элегантно.

Ответ №3:

Каждая строка в вашем 2D-массиве помещается из конца в конец в вашем 1D-массиве. i указывает, в какой строке вы находитесь, и j указывает столбец (как далеко в этой строке). поэтому, если вы находитесь в ith строке, вам нужно разместить i полные строки от конца до конца, а затем добавить j к ним дополнительные, чтобы получить индекс одного массива.

Так что это будет что-то вроде
singleDimIndex = array[0].length * i j

Ответ №4:

i*8 j (предполагая, что 8-это горизонтальная ширина)

Ответ №5:

Вы можете использовать этот класс ArrayConvertor для преобразования 2D-массивов в 1D-массивы и обратно.

Будьте осторожны: преобразование 2D-массива в обычный работает только с матрицей.

 public class ArrayConvertor {  static public int[] d2Tod1(int[][] array){   int[] newArray = new int[array.length*array[0].length];   for (int i = 0; i lt; array.length;   i)   for (int j = 0; j lt; array[i].length;   j) {  newArray[i*array[0].length j] = array[i][j];  }   return newArray;  }   static public int[][] d1Tod2(int[] array, int width){   int[][] newArray = new int[array.length/width][width];   for (int i = 0; i lt; array.length;   i) {  newArray[i/width][i%width] = array[i];  }   return newArray;  } }  

И немного кода для тестирования:

 public class JavaMain{  public static void main(String[] args) {  int[][] arr2D_1 = new int[4][8];   byte counter=0;  for (int i = 0; i lt; 4; i  )   for (int j = 0; j lt; 8; j  ) {  arr2D_1[i][j] = counter  ;  }   int[]arr1D = ArrayConvertor.d2Tod1(arr2D_1);  int[][] arr2D_2 = ArrayConvertor.d1Tod2(arr1D, 8);   boolean equal = true;  for (int i = 0; i lt; arr2D_1.length; i  )   for (int j = 0; j lt; arr2D_1[0].length; j  ){   if(arr2D_1[i][j]!=arr2D_2[i][j]) equal=false;  }   System.out.println("Equal: " equal);  } }  

Вывод: Равно: верно

Комментарии:

1. Я не думаю, что это работает, если у вас массив больше 8!!