Как вернуть массив с индексами определенного int из другого массива

#java #arrays

Вопрос:

Я начинающий студент Java, и я пытался написать метод, который перечисляет все индексы определенного int в массиве. До сих пор я сохранял значение этого int в соответствующем индексе в другом массиве, но лучшее, что я могу сделать, это установить значения всех других индексов, которые не равны исходному int, равным -1.

Я думаю, что мне нужно сохранить значение i в массиве и удалить все-1, но я не знаю, как это сделать. Кстати, эти значения равны -1, потому что все мои массивы в этой программе содержат числа в диапазоне от 0 до 100. Что бы я сделал, если бы возможно, чтобы в этом массиве могло быть любое число?

Также, несомненно, существует более простой или эффективный способ сделать это.

 public static int[] maxValueIndex(int[] arr, int targetValue, int x) {
    
    int[] maxValue = new int[x];
    
    
    for (int i = 0; i < arr.length; i  ) {
        if (arr[i] == targetValue) {
            maxValue[i] = arr[i];
        } else {
            maxValue[i] = -1;
        }
        
    }       
    return maxValue;
    }
 

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

1. Загляните в Set (google) и добавьте к этому индексы.

2. >…и удалите все-1, но я не знаю, как это сделать. < Ну, вы не можете ничего удалить из массива. Вы могли бы сжать его, хотя

3. возможно, если вы дадите некоторые примеры данных и результатов, это поможет лучше понять.

4. Если вы находитесь в процессе обучения и в постепенном режиме, и вы хотите избежать динамических контейнерных классов, то вы можете делать то, что вам нужно, с простыми массивами. Вам не нужно использовать код по ссылке, которую я опубликовал , который использует Integer , а не int , но это может дать вам несколько идей. По сути, если вы хотите удалить избыточные элементы -1, вам придется создать новый массив, чтобы вы могли подсчитать все элементы, которые не являются -1, чтобы найти нужный вам размер.

Ответ №1:

Если я правильно понял ваш запрос, то вам нужен массив со всеми такими индексами i , что arr[i]==targetValue . Мы можем добиться этого эффективно, используя любую динамическую структуру данных. Например, используйте an ArrayList и продолжайте добавлять все нужные индексы один за другим, затем преобразуйте список в массив и верните его.
Что-то вроде этого:

 List<Integer> index = new ArrayList<Integer>();
for (int i = 0; i < arr.length; i  )
{
    if (arr[i] == targetValue)
        index.add( i );
}
int[] maxValue = index.stream().mapToInt(Integer::intValue).toArray();
return maxValue;
 

Ответ №2:

Если требуется использовать массивы только для решения этой задачи, может потребоваться два этапа, чтобы создать сжатый массив, содержащий только допустимые индексы:

  1. Найдите количество совпадений, а затем создайте и заполните компактный массив
 public static int[] getTargetIndexes(int targetValue, int ... arr) {
    int n = arr.length;
    int targetCount = 0;
    for (int i = 0; i < n; i  ) {
        if (arr[i] == targetValue) {
            targetCount  ;
        }
    } 
    
    int[] indexes = new int[targetCount];

    for (int i = 0, j = 0; j <targetCount amp;amp; i < n; i  ) {
        if (arr[i] == targetValue) {
            indexes[j  ] = i;
        }
    }
    
    return indexes;
}
 
  1. Создайте массив одинаковой длины, заполните его и затем уплотните с помощью Arrays.copyOf :
 public static int[] getTargetIndexes(int targetValue, int ... arr) {
    int n = arr.length;
    int[] indexes = new int[n];

    int targetCount = 0;
    for (int i = 0; i < n; i  ) {
        if (arr[i] == targetValue) {
            indexes[i] = i;
            targetCount  ;
        } else {
            indexes[i] = -1;
        }
    }
    
    for (int i = 0, j = 0; j < targetCount amp;amp; i < n; i  ) {
        if (indexes[i] > -1) {
            indexes[j  ] = i;
        }
    }
    
    return Arrays.copyOf(indexes, targetCount); // truncate bad indexes
}
 

Кроме того, сигнатура метода использует vararg для передачи входного массива в виде последовательности int — аргумент vararg int ... arr должен быть последним.


Если можно использовать потоковый API, задача может быть удобно решена декларативным способом:

 public static int[] getTargetIndexes(int targetValue, int ... arr) {   
    return IntStream.range(0, arr.length) // get stream of indexes
            .filter(i -> arr[i] == targetValue) // keep only matching indexes
            .toArray(); // build output array
}