-1

I am trying to find the integer that appears an odd numbers of time, but somehow the tests on qualified.io are not returning true. May be there is something wrong with my logic?

The problem is that in an array [5,1,1,5,2,2,5] the number 5 appears 3 times, therefore the answer is 5. The method signature wants me to use List<>. So my code is below.

public static List<Integer> findOdd( List<Integer> integers ) {

    int temp = integers.size();

        if (integers.size() % 2 == 0) {
            //Do something here.
        }
    return integers;
    }
}

I need to understand couple things. What is the best way to check all elements inside integers list, and iterate over to see if any similar element is present, if yes, return that element.

sahmad
  • 142
  • 1
  • 8
  • 1
    Have you looked into java streams? – Nitishkumar Singh Apr 21 '18 at 06:43
  • *"but somehow the tests [...] are not returning true"* Perhaps the fact that you're missing some code (`//Do something here.`) might have something to do with it. – Andreas Apr 21 '18 at 06:52
  • 1
    Perhaps you could do some **research**, e.g. read answers to questions like [Java count occurrence of each item in an array](https://stackoverflow.com/q/8098601/5221149). – Andreas Apr 21 '18 at 06:54
  • If you know there's only one integer that appears an odd number of times, you can just XOR everything to get the answer. – Dawood ibn Kareem Apr 21 '18 at 06:58
  • The code shown does not even try to address the actual problem. Before writing code one should think of the algorithm for a solution, which was not done in this case, it shows that no research has been done. – Oleg Sklyar Apr 21 '18 at 07:41

4 Answers4

1

If you are allowed to use java 8, you can use streams and collectors for this:

Map<Integer, Long> collect = list.stream()
        .collect(Collectors.groupingBy(Function.identity(), Collectors.counting()));

Given a list with integers, this code will generate a map, where the key is the actual number and value is number of repetitions.

You just have to iterate through map and find out what are you interested in.

Schidu Luca
  • 3,897
  • 1
  • 12
  • 27
0

You want to set up a data structure that will let you count every integer that appears in the list. Then iterate through your list and do the counting. When you're done, check your data structure for all integers that occur an odd number of times and add them to your list to return.

Something like:

public static List<Integer> findOdd(List<Integer> integers) {
    Map<Integer, MutableInt> occurrences = new HashMap<>(); // Count occurrences of each integer
    for (Integer i : integers) {
        if (occurrences.containsKey(i)) {
            occurrences.get(i).increment();
        } else {
            occurrences.put(i, new MutableInt(1));
        }
    }
    List<Integer> answer = new ArrayList<>();
    for (Integer i : occurrences.keySet()) {
        if ((occurrences.get(i) % 2) == 1) { // It's odd
            answer.add(i)
        }
    }
    return answer;
}

MutableInt is an Apache Commons class. You can do it with plain Integers, but you have to replace the value each time.

If you've encountered streams before you can change the second half of the answer above (the odd number check) to something like:

return occurrences.entrySet().stream()
         .filter(i -> i % 2 == 1)
         .collect(Collectors.toList());

Note: I haven't compiled any of this myself so you may need to tweak it a bit.

dave
  • 11,641
  • 5
  • 47
  • 65
  • The use of `MutableInt` is very elegant, but it is unfortunate that you provide a complete solution to an OP who failed to do his home work first, failed to provide any evidence of his own research. Essentially you are just doing home work for them doing them little good :( – Oleg Sklyar Apr 21 '18 at 07:43
  • I did consider that, however in my view, the OP was struggling a bit and unlikely to get there themselves. If that's true then hopefully this did more good than harm. – dave Apr 21 '18 at 07:57
  • Fair enough, we never know – Oleg Sklyar Apr 21 '18 at 07:58
0
int findOdd(int[] nums) {
  Map<Integer, Boolean>evenNumbers = new HashMap<>();
  nums.forEach(num -> {
    Boolean status = evenNumbers.get(num);
    if(status == null) {
      evenNumbers.put(num, false);
    }else{
      evenNumbers.put(num, !status);
    }
  });
  // Map holds true for all values with even occurrences
  Iterator<Integer> it = evenNumbers.keySet().iterator();
  while(it.hasNext()){
    Integer key = it.next();
    Boolean next = evenNumbers.get(key);
    if(next == false){
      return key;
    }
  }
}
Jason Palmer
  • 99
  • 2
  • 8
0

You could use the reduce method from the IntStream package.

Example:

stream(ints).reduce(0, (x, y) -> x ^ y);
Adrian Mole
  • 49,934
  • 160
  • 51
  • 83