Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Java 8 shows this error. Local variable itemList defined in an enclosing scope must be final or effectively final

I am writing the code using java 8 but I iterate a List and then find RestaurantOrderBook using category type. and put that List into a Map. it shows this error:

Local variable itemList defined in an enclosing scope must be final or effectively final

Query query = new Query();
String categ = category;
query.addCriteria(Criteria.where("restaurantId").is(restaurantId));

List<RestaurantOrderBook> itemList = new ArrayList<RestaurantOrderBook>();
itemList = mongoTemplate.find(query, RestaurantOrderBook.class);
System.out.println("size : " + itemList.size());
Map<String , List<RestaurantOrderBook>> map = new HashMap<String , List<RestaurantOrderBook>>();
        Arrays.asList("TakeAway", "Dining").forEach(e ->{

//Following line throws error:              
List<RestaurantOrderBook> list  = itemList.stream().filter(a -> !a.getOrderType().isEmpty() && a.getOrderType().equals(e)).collect(Collectors.toList());
                map.put(e, list);
        });

I have an another situation:

@Override
    public EventReportRewardsPoints eventReportRewardsPoints(String organizerId) {
        try{
            List<Event> listOfEvents = eventRepo.findByOrganizerId(organizerId);
            EventReportRewardsPoints eventTransReport = new EventReportRewardsPoints();
            Integer soldTics = 0;
            Double totalRevenue = 0d;
            Integer soldToday  = 0;

            Integer findTotalAvailableTics = 0;
            Integer findTotalQtytics = 0;

            for (Event event : listOfEvents) {
                List<EventTicket> eventTicket = eventTicketRepo.findByEventId(event.getId());

                Integer sumOfAvailabletics = eventTicket.stream()
                        .mapToInt(EventTicket::getRemainingTickets).sum();
                findTotalAvailableTics = findTotalAvailableTics + sumOfAvailabletics;

                Integer sumOfQtytics = eventTicket.stream().mapToInt(EventTicket::getQty).sum();
                findTotalQtytics  = findTotalQtytics + sumOfQtytics;

                List<EventTicketBook> listOfEventsTic = eventTicketBookRepository.findByEventId(event.getId());
                for (EventTicketBook eventTicketBook : listOfEventsTic) {
                    Double sumOfSales = eventTicketBook.getTickets().stream().mapToDouble(EventTicket::getPrice).sum();
                    totalRevenue = totalRevenue + sumOfSales;
                    Date now = new Date();
                    System.out.println("create date : " + eventTicketBook.getCreateOn());
                    /*if(now.compareTo(eventTicketBook.getCreateOn()) == 0){
                        Integer sumOfSoldToday = eventTicketBook.getTickets().stream().mapToInt(EventTicket::getQty).sum();
                        soldToday = soldToday + sumOfSoldToday;
                    }*/
                }
            }
            System.out.println("findTotalQtytics : " + findTotalQtytics);
            System.out.println("findTotalAvailableTics : " + findTotalAvailableTics);
            soldTics = findTotalQtytics - findTotalAvailableTics;
            eventTransReport.setTotalRevenue(totalRevenue);
            eventTransReport.setSoldToday(soldToday);
            eventTransReport.setTicketsSold(soldTics);
            return eventTransReport;
        }catch(Exception e ){
            e.printStackTrace();
        }
        return null;
    }

How do i achive this using lamda expression.??

like image 959
Navaneethan Arun Avatar asked Jan 04 '23 08:01

Navaneethan Arun


1 Answers

You are using itemList within a lambda expression. Therefore it has to be final.

Java 8 introduces the new concept of effectivly final, which means, the compiler checks, if a used variable is final in usage and does not force the developer to explicitly declare it as final.

So if you change your code to

final List<RestaurantOrderBook> itemList = new ArrayList<RestaurantOrderBook>();

you will see, that the compiler gives you an error at:

itemList = mongoTemplate.find(query, RestaurantOrderBook.class);

because you are reasigning itemList. That is why itemList is not effectivly final as well. If you squash these two lines to

List<RestaurantOrderBook> itemList = mongoTemplate.find(query, RestaurantOrderBook.class);

it should work.

like image 193
wumpz Avatar answered Jan 13 '23 18:01

wumpz