001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.camel.util; 018 019import java.io.Closeable; 020import java.io.IOException; 021import java.util.Iterator; 022import java.util.NoSuchElementException; 023import java.util.function.Predicate; 024 025/** 026 * A filtering iterator 027 */ 028public class FilterIterator<T> implements Iterator<T>, Closeable { 029 030 private Iterator<T> it; 031 private Predicate<T> filter; 032 private T next; 033 private boolean closed; 034 035 public FilterIterator(Iterator<T> it) { 036 this(it, null); 037 } 038 039 public FilterIterator(Iterator<T> it, Predicate<T> filter) { 040 this.it = it; 041 this.filter = filter; 042 } 043 044 @Override 045 public void close() throws IOException { 046 try { 047 IOHelper.closeIterator(it); 048 } finally { 049 // we are now closed 050 closed = true; 051 next = null; 052 } 053 } 054 055 @Override 056 public boolean hasNext() { 057 if (next == null) { 058 next = checkNext(); 059 } 060 return next != null; 061 } 062 063 @Override 064 public T next() { 065 if (next == null) { 066 next = checkNext(); 067 } 068 if (next != null) { 069 T ep = next; 070 next = null; 071 return ep; 072 } 073 throw new NoSuchElementException(); 074 } 075 076 @Override 077 public void remove() { 078 it.remove(); 079 } 080 081 protected T checkNext() { 082 while (!closed && it.hasNext()) { 083 T ep = it.next(); 084 if (ep != null && (filter == null || filter.test(ep))) { 085 return ep; 086 } 087 } 088 return null; 089 } 090 091}