
package de.ivu.elect.business.person.control;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.function.Function;

import de.ivu.elect.business.person.entity.Personendaten;
import de.ivu.elect.jee.entity.Entity;
import de.ivu.elect.util.MapBuilder;

public abstract class AbstractAehnlichePersonenFinder<Person extends Personendaten, WahlOderWahltermin extends Entity> {

  public List<Person> findeAehnlichePersonen(Collection< ? extends Person> personen) {

    Map<WahlOderWahltermin, List<Person>> wahlhelferNachWahltermin = mappePersonenNachWahlBzwWahltermin(personen);
    List<Person> potentielleDubletten = new ArrayList<>();

    for (Entry<WahlOderWahltermin, List<Person>> entry : wahlhelferNachWahltermin.entrySet()) {
      potentielleDubletten.addAll(findeAehnlichePersonen(entry.getKey(), entry.getValue()));
    }

    return potentielleDubletten;

  }

  protected abstract List< ? extends Person> findeAehnlichePersonen(WahlOderWahltermin wahlOderWahltermin,
      List<Person> personen);

  private Map<WahlOderWahltermin, List<Person>> mappePersonenNachWahlBzwWahltermin(
      Collection< ? extends Person> personen) {

    return MapBuilder.newMapMultipleEntriesFrom(personen, getPersonNachWahlOderWahlterminFunction());
  }

  protected abstract Function<Person, WahlOderWahltermin> getPersonNachWahlOderWahlterminFunction();

}
