How do you not display repeated JAVA values

Asked

Viewed 119 times

0

Good evening, I managed to get it to display all the values along with the repeated ones and only the repeated ones, I wanted to know how to display only the numbers that were not repeated. Ex: 1,2,3,2,4 = 1,3,4

Thanks in advance. That was the code I made:

   int[] vetor3 = {4,6,2,2,8,2,0}; 
   int aux = 0;
   for (int  i = 0; i < vetor3.length; i++){
   for (int j = i+1; j < vetor3.length; j++){
   if (vetor3[j] == vetor3[i]){
   System.out.println("Vai: " +vetor3[j]);
   }
   }
   }

3 answers

1

Depends.

Whether the order of the elements is important, that is, if they should be printed in the same order they appear in the array, you can use the another answer, but remembering that it is a quadratic algorithm: for each element of the array, it traverses the entire array again: in the elements that are repeated, the loop internal is interrupted in the middle, but for those that do not repeat, the whole array is traversed again (when there are many repetitions, the algorithm would be near or below the sub-quadratic; in the best case, in which all elements are equal, it would be linear; in the worst case, in which none - or most - does not repeat, it is quadratic).

Of course for small arrays the difference is insignificant (after all, for few data, everything is fast), but start working with larger arrays and this starts to make a considerable difference.

Therefore, a better alternative would be to go through the array only once, and keep a count of the elements. Then, I print only those who had the count equal to 1. For that I will use a Map, and to keep the elements in order, a LinkedHashMap (that keeps the elements in the order they were inserted). For this you will need to import them:

import java.util.LinkedHashMap;
import java.util.Map;

Then you just do:

int[] vetor = {4, 6, 2, 2, 8, 2, 0};
Map<Integer, Integer> counter = new LinkedHashMap<>(vetor.length);
for (int n : vetor) { // para cada elemento do array
    if (!counter.containsKey(n)) { // se não está no map, adiciona
        counter.put(n, 1);
    } else { // se já está, atualiza a contagem
        counter.put(n, counter.get(n) + 1);
    }
}
for (Map.Entry<Integer, Integer> entry : counter.entrySet()) {
    if (entry.getValue() == 1) { // imprime somente se a contagem for 1
        System.out.println(entry.getKey());
    }
}

That is, I run the array only once, to create the Map containing the quantities of each element, and then run the map, printing the ones that occurred only once. It is no longer a quadratic algorithm, but rather linear, but has the cost of maintaining the Map (there is no way, in computing everything is trade-off).


But if the order is not important, that is, I just want to know the elements that occur once, but I don’t need to return them in the same order that they occur in the array, an alternative is to first sort the array. Then it is enough to see whether an element is equal to its predecessor and predecessor (taking care not to check the predecessor of the former, nor the predecessor of the latter):

Arrays.sort(vetor); // ordena o array
for (int i = 0; i < vetor.length; i++) {
    if ((i == 0 && vetor[0] != vetor[1]) // se é o primeiro, e não é igual ao segundo
        // ou, se é o último, e não é igual ao penúltimo
        || (i == vetor.length - 1 && vetor[vetor.length - 2] != vetor[vetor.length - 1])
        // ou, se não é o primeiro nem o último, e é diferente do anterior e do próximo
        || (vetor[i] != vetor[i + 1] && vetor[i] != vetor[i - 1])) {
        System.out.println(vetor[i]);
    }
}

In this case, the ordination is - according to the documentation - (nlogn), which is already better than the quadratic algorithm. After sorting, we go through the array once, checking its elements.

Although it is not linear, there is no expense of creating a Map. But there is the side effect of ordering the original array (which may not always be what you want - I have already said that in computing everything is trade-off? You have to choose what makes the most sense in each case, and of course, testing with the actual data to know if using one algorithm or another makes any significant difference). Anyway, the options are there.

1


Apparently your solution only prints the repeating numbers to print the numbers that are not repeated in the vetor, you will need to go through your vetor, then check if a specific position repeats and print it or not depending on the case. That is, you would need a logic to verify if a certain number is in the vector and another to print the values, then you would have to join them.

Checking whether a number is in the vector

To check whether a number is in the vector or not, you need to go through its entire vector and compare all positions with the number until you find a repeated value. You can do this using the following logic:

int a = 7;
for (int i = 0; i < vetor.length; i++) {
    if (a == vetor[i]) // Se esse if ativar entao o numero 7 ta no vetor
}

Printing the values of the vector

Now we must make another logic to print the numbers of the vector. The code for printing would be as follows:

for (int i = 0; i < vetor.length; i++) {
    System.out.println(vetor[i]);
}

The above code would print all values, not to print the repeated ones, we must join the two codes. The union between them would be like this:

for (int i = 0; i < vetor.length; i++) {
    boolean repetiu = false;

    for (int j = 0; j < vetor.length; j++) {
        if (vetor[i] == vetor[j] && i != j) { // verificando repeticao
            repetiu = true; // numero repetiu
            break; // se repetiu ao menos uma vez, entao nao eh necessario
            // percorrer todo o vetor
        }
    }

    if (!repetiu) System.out.println(" " + vetor[i] + " ");
}

The above code checks if an element exists in the vector, that is, if we have vetor[3], then he checks if the number within vetor[3] exists in the vector, if it exists, then the variable repetiu will be true and the print will not be activated, otherwise the number will be printed on the screen. Note that the expression i != j serves to prevent the number from being compared to itself (if this occurs, then the variable repetiu would always be true). If any part has not been made clear, you can do the table test to better understand the logic.

See the code working here.

-1

Hello, you can convert into a stream and use the method distinct to "filter" the repeaters.

import java.util.Arrays;

public class MyClass {
    public static void main(String args[]) {

      String[] array = {"a", "b", "a", "c"};

      Arrays.stream(array)
        .distinct()
        .forEach(System.out::println);
    }
}

Exit:

to b c

You can use the filter with a logic to remove duplicates, with the frequency that returns the amount of it:

Arrays.stream(array)
  .filter(i -> Collections.frequency(Arrays.asList(array), i) < 2)
  .forEach(System.out::println);

Exit:

b c

  • I understood and managed to do this way you spoke, thanks for the tip, but you know how to not show the repeated numbers, "A , B, C, A" = "B, C" type like this?

  • Sorry @Tantofaz had got it wrong.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.