package com.webucator.test;

import com.webucator.person.Person;
import java.util.*;
import java.util.stream.*;

public class TestStreamsAndLambdas {
    public static void main(String args[]) {
        Person[] personArray={ new Person("Stephen", "Withrow"),
                new Person("Mary", "Smith"),
                new Person("Dave", "Dunn"),
                new Person("Nat", "Dunn")};
        List<Person> persons = Arrays.asList(personArray);
        // filter persons with last name of Dunn and print
        System.out.println("Printing from stream filtered for last name \"Dunn\":");
        persons.stream()
                .filter(p -> p.getLastName().equals("Dunn"))
                .forEach(p-> System.out.println(p));

        // filter persons with first name of Stephen and last name of Withrow and collect as a list
        List<Person> listFromStream=persons.stream()
                .filter(p -> p.getFirstName().equals("Stephen") && p.getLastName().equals("Withrow"))
                .collect(Collectors.toList());
        System.out.println("Printing from list created from stream filtered for first name \"Stephen\" and last name \"Withrow\":");
        for (Person p: listFromStream) {
            System.out.println(p);
        }
        // repeat last operation except pass method reference to filter instead of lambda
        List<Person> listFromStream2=persons.stream()
                .filter(TestStreamsAndLambdas::checkName)
                .collect(Collectors.toList());
        System.out.println("List using method reference for first name \"Stephen\" and last name \"Withrow\":");
        for (Person p: listFromStream) {
            System.out.println(p);
        }
        // group persons by last name and value of count of persons in each group
        Map<String, Long> lastNameCount = persons.stream()
                .collect(Collectors.groupingBy((p -> p.getLastName()), Collectors.counting()));
        for (Map.Entry<String, Long> entry : lastNameCount.entrySet()) {
            System.out.println("Count of persons with last name " + entry.getKey() + " is " +
                    entry.getValue());
        }

        // map array list data into a list of sorted first names
        List<String> firstNames = persons.stream().map(person -> person.getFirstName())
                .sorted()
                .collect(Collectors.toList());
        System.out.println("Printing from sorted list of first names created from stream:");
        for (String firstName : firstNames) {
            System.out.println(firstName);
        }
    }

    public static boolean checkName(Person p) {
        return p.getFirstName().equals("Stephen") && p.getLastName().equals("Withrow");
    }
}