Как решить вложенные циклы, используя Java лямбду - PullRequest
0 голосов
/ 15 января 2020

У меня есть объект, который использует 2 вложенных цикла для поиска подходящих процессов на основе pid. Цель состоит в том, чтобы собрать все процессы, которые происходят в кортеже. Кортеж используется для хранения двух процессов, которые имеют одно и то же имя процесса, но разные идентификаторы процессов. Процессы всегда порождаются парами.

Вот фрагмент класса.

class Process{

  private String name;
  private String pid;
  private String processName;

   public boolean equals(Object o) {
    if (this == o) return true;
    if (!(o instanceof Process)) return false;
    Process that = (Process) o;
    return Objects.equals(pid , that.pid);
    etc...
 }

   class Tuple {
      Process parent;
      Process child;
      Tuple(Process first, Process second){
      }
   }

Вот как я обрабатываю список заказов:

  List<Process> processes..
  List<Tuple> tuples = new ArrayList<>();
  for( Process p0 : processes){
     for(Process p1 : processes){
        if(p0.processName.equals(p1.processName)){
          p1.pid != p0.pid;
          Tuple tp= new Tuple(p0, p1);
          tuples.add(tp);
        }
     } 

  }

Как я могу использовать лямбда-функцию для выполнения sh этого в Java 12?

1 Ответ

0 голосов
/ 15 января 2020

Когда вы запрашиваете "лямбда-функцию для выполнения sh этого" , я полагаю, что вы на самом деле спрашиваете, как это сделать, используя потоков .

Я предполагаю, что Tuple - это отдельный класс верхнего уровня или static вложенный класс, а не внутренний класс, как это в настоящее время показано в вопросе.

List<Tuple> tuples = processes.stream()
        .flatMap(p0 -> processes.stream()
                .filter(p1 -> p0.getPid() != p1.getPid()
                           && p0.getProcessName().equals(p1.getProcessName()))
                .map(p1 -> new Tuple(p0, p1)))
        .collect(Collectors.toList());

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

List<Tuple> tuples2 = processes.stream()
        .collect(Collectors.groupingBy(Process::getProcessName))
        .values().stream()
        .filter(list -> list.size() > 1)
        .flatMap(list -> list.stream()
                .flatMap(p0 -> list.stream()
                        .filter(p1 -> p0.getPid() != p1.getPid())
                        .map(p1 -> new Tuple(p0, p1))
                )
        )
        .collect(Collectors.toList());

Я надеюсь, вы понимаете, что все кортежи будут иметь зеркала, т.е. для каждого tuple(a,b), который вы собираетесь также иметь tuple(b,a). Чтобы предотвратить это, измените условия p0.getPid() != p1.getPid() на p0.getPid() < p1.getPid().

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...