๐ํ๋ก๊ทธ๋๋จธ์ค ๋ฐฑ์๋ ๋ฐ๋ธ์ฝ์ค 4๊ธฐ ๊ต์ก๊ณผ์ ์ ๋ฃ๊ณ ์ ๋ฆฌํ ๊ธ์
๋๋ค.๐
Collection
List
- List ์ธํฐํ์ด์ค๋ ์์๊ฐ ์๋ ๋ฐ์ดํฐ์ ์งํฉ์ ํํํฉ๋๋ค.
- ๋ฐ์ดํฐ์ ์ค๋ณต์ ํ์ฉํฉ๋๋ค.
- ๊ตฌํ ํด๋์ค๋ก๋ ArrayList, LinkedList ๋ฑ์ด ์์ต๋๋ค.
- ์ธ๋ฑ์ค๋ฅผ ์ฌ์ฉํ์ฌ ์์์ ์ ๊ทผํ ์ ์์ต๋๋ค.
Set
- Set ์ธํฐํ์ด์ค๋ ์์๊ฐ ์๋ ๊ณ ์ ํ ๋ฐ์ดํฐ์ ์งํฉ์ ํํํฉ๋๋ค.
- ๋ฐ์ดํฐ์ ์ค๋ณต์ ํ์ฉํ์ง ์์ต๋๋ค.
- ๊ตฌํ ํด๋์ค๋ก๋ HashSet, TreeSet ๋ฑ์ด ์์ต๋๋ค.
- ํด์ ๊ธฐ๋ฐ ๋๋ ์ ๋ ฌ๋ ์์๋ก ์์๋ฅผ ์ ์ฅํ๊ณ ๊ด๋ฆฌํฉ๋๋ค.
Map
- Map ์ธํฐํ์ด์ค๋ ํค์ ๊ฐ์ผ๋ก ์ด๋ฃจ์ด์ง ๋ฐ์ดํฐ์ ์งํฉ์ ํํํฉ๋๋ค.
- ํค-๊ฐ ์์ผ๋ก ๋ฐ์ดํฐ๋ฅผ ์ ์ฅํ๊ณ ๊ด๋ฆฌํฉ๋๋ค.
- ํค๋ ๊ณ ์ ํด์ผ ํ๋ฉฐ, ๊ฐ์ ์ค๋ณต์ด ๊ฐ๋ฅํฉ๋๋ค.
- ๊ตฌํ ํด๋์ค๋ก๋ HashMap, TreeMap, LinkedHashMap ๋ฑ์ด ์์ต๋๋ค.
Queue
- Queue ์ธํฐํ์ด์ค๋ ์ ์
์ ์ถ(FIFO) ํํ์ ๋ฐ์ดํฐ ๊ตฌ์กฐ๋ฅผ ํํํฉ๋๋ค.
- ๋ฐ์ดํฐ์ ์ฝ์
์ ํ์ชฝ ๋์์, ์ญ์ ๋ ๋ค๋ฅธ ํ์ชฝ ๋์์ ์ด๋ฃจ์ด์ง๋๋ค.
- ๊ตฌํ ํด๋์ค๋ก๋ LinkedList, PriorityQueue ๋ฑ์ด ์์ต๋๋ค.
Stack
- Stack ํด๋์ค๋ ํ์
์ ์ถ(LIFO) ํํ์ ๋ฐ์ดํฐ ๊ตฌ์กฐ๋ฅผ ํํํฉ๋๋ค.
- ๋ฐ์ดํฐ์ ์ฝ์
๊ณผ ์ญ์ ๊ฐ ๊ฐ์ ์ชฝ์์ ์ด๋ฃจ์ด์ง๋๋ค.
- ์ฃผ์ ๋ฉ์๋๋ก๋ push(), pop(), peek() ๋ฑ์ด ์์ต๋๋ค.
Iterator
public class Main {
public static void main(String[] args) {
List<String> fruits = new ArrayList<>();
fruits.add("Apple");
fruits.add("Banana");
fruits.add("Orange");
// Iterator๋ฅผ ์ฌ์ฉํ์ฌ ์ปฌ๋ ์
์ ์์์ ์ ๊ทผ
Iterator<String> iterator = fruits.iterator();
while (iterator.hasNext()) {
String fruit = iterator.next();
System.out.println(fruit);
}
// Iterator๋ฅผ ์ฌ์ฉํ์ฌ ํน์ ์กฐ๊ฑด์ ์์ ์ญ์
iterator = fruits.iterator();
while (iterator.hasNext()) {
String fruit = iterator.next();
if (fruit.equals("Banana")) {
iterator.remove(); // ํ์ฌ ์์ ์ญ์
}
}
System.out.println(fruits); // ์ถ๋ ฅ: [Apple, Orange]
}
}
- ์ปฌ๋ ์
์ ์์๋ฅผ ์์ฐจ์ ์ผ๋ก ์ ๊ทผํ ์ ์์ต๋๋ค.
- hasNext() ๋ฉ์๋๋ฅผ ํตํด ๋ค์ ์์์ ์กด์ฌ ์ฌ๋ถ๋ฅผ ํ์ธํ๊ณ , next() ๋ฉ์๋๋ฅผ ํธ์ถํ์ฌ ๋ค์ ์์๋ฅผ ์ป์ต๋๋ค.
- ์์๋ฅผ ์์ ํ๊ฒ ์ญ์ ํ ์ ์์ต๋๋ค.
- Iterator๋ฅผ ํตํด remove() ๋ฉ์๋๋ฅผ ํธ์ถํ๋ฉด ํ์ฌ ์์๋ฅผ ์ญ์ ํฉ๋๋ค.
- Iterator๋ ์๋ฐ์ ๋ชจ๋ ์ปฌ๋ ์
์ธํฐํ์ด์ค์์ ์ฌ์ฉํ ์ ์์ต๋๋ค.
Stream
- ์๋ฐ 8๋ถํฐ ๋์
๋ Stream์ ๋ฐ์ดํฐ์ ํ๋ฆ์ ๋ํ๋ด๋ฉฐ, ์ปฌ๋ ์
์ ์ ์ฅ๋ ์์๋ค์ ๋ค์ํ ์ฐ์ฐ์ ํตํด ์ฒ๋ฆฌํฉ๋๋ค.
- ๋ณ๋ ฌ ์คํธ๋ฆผ์ ์ฌ์ฉํ๋ฉด, ๋ฐ์ดํฐ๋ฅผ ๋ณ๋ ฌ์ ์ผ๋ก ์ฒ๋ฆฌํ์ฌ ์ฑ๋ฅ์ ํฅ์์ํฌ ์ ์์ต๋๋ค.
- Stream์ ํ ๋ฒ ์ฌ์ฉํ ํ์๋ ์ฌ์ฌ์ฉํ ์ ์์ต๋๋ค.
- ์ค๊ฐ ์ฐ์ฐ๊ณผ ์ต์ข
์ฐ์ฐ์ผ๋ก ๊ตฌ๋ถ๋ฉ๋๋ค.
- ์ค๊ฐ ์ฐ์ฐ์ ๋ฐ์ดํฐ๋ฅผ ๋ณํํ๊ฑฐ๋ ํํฐ๋งํ๋ ์์
์
๋๋ค.
- ์ต์ข
์ฐ์ฐ์ ๊ฒฐ๊ณผ๋ฅผ ๋ฐํํฉ๋๋ค.
์ค๊ฐ ์ฐ์ฐ
filter(Predicate<T> predicate)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
List<Integer> evenNumbers = numbers.stream()
.filter(n -> n % 2 == 0)
.collect(Collectors.toList());
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(evenNumbers); // [2, 4]
- ์ฃผ์ด์ง ์กฐ๊ฑด์ ๋ง๋ ์์๋ค๋ก ๊ตฌ์ฑ๋ ์๋ก์ด Stream์ ๋ฐํํฉ๋๋ค.
map(Function<T, R> mapper)
List<String> names = Arrays.asList("Alice", "Bob", "Charlie");
List<Integer> nameLengths = names.stream()
.map(String::length)
.collect(Collectors.toList());
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(nameLengths); // [5, 3, 7]
- ์์๋ฅผ ๋ค๋ฅธ ์์๋ก ๋ณํํ์ฌ ์๋ก์ด Stream์ ๋ฐํํฉ๋๋ค.
distinct()
List<Integer> numbers = Arrays.asList(1, 2, 2, 3, 3, 3, 4, 5, 5);
List<Integer> distinctNumbers = numbers.stream()
.distinct()
.collect(Collectors.toList());
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(distinctNumbers); // [1, 2, 3, 4, 5]
- ์ค๋ณต๋ ์์๋ฅผ ์ ๊ฑฐํ ์๋ก์ด Stream์ ๋ฐํํฉ๋๋ค.
sorted()
List<Integer> numbers = Arrays.asList(5, 3, 1, 4, 2);
List<Integer> sortedNumbers = numbers.stream()
.sorted()
.collect(Collectors.toList());
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(sortedNumbers); // [1, 2, 3, 4, 5]
- ์์๋ฅผ ์ ๋ ฌํ ์๋ก์ด Stream์ ๋ฐํํฉ๋๋ค.
limit(long maxSize)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
List<Integer> limitedNumbers = numbers.stream()
.limit(3)
.collect(Collectors.toList());
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(limitedNumbers); // [1, 2, 3]
- ์์์ ๊ฐ์๋ฅผ maxSize๋งํผ ๊ฐ๋ ์๋ก์ด Stream์ ๋ฐํํฉ๋๋ค.
์ต์ข
์ฐ์ฐ
forEach(Consumer<T> action)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream()
.forEach(System.out::println); // ๊ฒฐ๊ณผ ์ถ๋ ฅ: ๊ฐ ์ซ์๊ฐ ํ ์ค์ฉ ์ถ๋ ฅ๋จ
- Stream์ ๊ฐ ์์์ ๋ํด ์ฃผ์ด์ง ๋์์ ์ํํฉ๋๋ค.
collect(Collector<T, A, R> collector)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
String concatenatedNumbers = numbers.stream()
.map(Object::toString)
.collect(Collectors.joining(", "));
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(concatenatedNumbers); // "1, 2, 3, 4, 5"
- Stream์ ์์๋ฅผ ์์งํ์ฌ ์ปฌ๋ ์
๋๋ ๋ค๋ฅธ ํํ๋ก ๊ฒฐ๊ณผ๋ฅผ ๋ฐํํฉ๋๋ค.
reduce(BinaryOperator<T> accumulator)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
// ๋ชจ๋ ์ซ์์ ํฉ ๊ตฌํ๊ธฐ
Optional<Integer> sum = numbers.stream()
.reduce((a, b) -> a + b);
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(sum.orElse(0)); // 15
- Stream์ ์์๋ค์ ๋ฐ๋ณต์ ์ผ๋ก ์กฐํฉํ์ฌ ์ต์ข
๊ฒฐ๊ณผ๋ฅผ Optional๋ก ๋ฐํํฉ๋๋ค.
count()
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
// ์์์ ๊ฐ์ ์ธ๊ธฐ
long count = numbers.stream()
.count();
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(count); // 5
- Stream์ ์์์ ๊ฐ์๋ฅผ ๋ฐํํฉ๋๋ค.
anyMatch(Predicate<T> predicate)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
boolean anyEvenNumber = numbers.stream()
.anyMatch(n -> n % 2 == 0);
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(anyEvenNumber); // true
- Stream์ ์์ ์ค ์กฐ๊ฑด์ ๋ง์กฑํ๋ ์์๊ฐ ํ๋๋ผ๋ ์กด์ฌํ๋ฉด true๋ฅผ ๋ฐํํ๊ณ , ๊ทธ๋ ์ง ์์ผ๋ฉด false๋ฅผ ๋ฐํํฉ๋๋ค.
allMatch(Predicate<T> predicate)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
boolean allGreaterThanZero = numbers.stream()
.allMatch(n -> n > 0);
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(allGreaterThanZero); // true
- Stream์ ๋ชจ๋ ์์๊ฐ ์กฐ๊ฑด์ ๋ง์กฑํ๋ฉด true๋ฅผ ๋ฐํํ๊ณ , ๊ทธ๋ ์ง ์์ผ๋ฉด false๋ฅผ ๋ฐํํฉ๋๋ค.
noneMatch(Predicate<T> predicate)
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
boolean noneGreaterThanFive = numbers.stream()
.noneMatch(n -> n > 5);
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(noneGreaterThanFive); // true
- Stream์ ๋ชจ๋ ์์๊ฐ ์กฐ๊ฑด์ ๋ง์กฑํ์ง ์์ผ๋ฉด true๋ฅผ ๋ฐํํ๊ณ , ๊ทธ๋ ์ง ์์ผ๋ฉด false๋ฅผ ๋ฐํํฉ๋๋ค.
findFirst()
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
Optional<Integer> firstEvenNumber = numbers.stream()
.filter(n -> n % 2 == 0)
.findFirst();
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(firstEvenNumber.orElse(-1)); // 2
- Stream์ ์ฒซ ๋ฒ์งธ ์์๋ฅผ Optional๋ก ๋ฐํํฉ๋๋ค.
- ์คํธ๋ฆผ์ ์์๊ฐ ์ ๋ ฌ๋์ด ์์ง ์๊ฑฐ๋, ํน์ ํ ์์๋ฅผ ์ฐพ๋ ๊ฒ์ด ์๋๋ผ๋ฉด ์ผ๋ฐ์ ์ผ๋ก findAny() ํจ์๋ฅผ ์ฌ์ฉํ๋ ๊ฒ์ด ์ข์ต๋๋ค.
findAny()
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
Optional<Integer> anyNumber = numbers.stream()
.findAny();
// ๊ฒฐ๊ณผ ์ถ๋ ฅ
System.out.println(anyNumber.orElse(-1)); // 1 or 2 or 3 or 4 or 5 (๋๋ค)
- Stream์์ ์์์ ์์๋ฅผ Optional๋ก ๋ฐํํฉ๋๋ค.
- ์คํธ๋ฆผ์ ์์๊ฐ ์ ๋ ฌ๋์ด ์๊ณ ์ฒซ ๋ฒ์งธ ์์๋ฅผ ์ฐพ์์ผ ํ๋ ๊ฒฝ์ฐ์๋ findFirst() ํจ์๋ฅผ ์ฌ์ฉํ๋ ๊ฒ์ด ์ข์ต๋๋ค.
Optional
public class Main {
public static void main(String[] args) {
String name = "John";
Optional<String> optionalName = Optional.of(name); // ๊ฐ์ด ์๋ Optional ์์ฑ
// ์กด์ฌ ์ฌ๋ถ ํ์ธ
boolean isEmpty = optionalName.isEmpty();
boolean isPresent = optionalName.isPresent();
// ๊ฐ ๊ฐ์ ธ์ค๊ธฐ
String retrievedName = optionalName.get();
// ๊ธฐ๋ณธ๊ฐ ์ค์
String defaultValue = optionalName.orElse("Default");
String defaultValueFromSupplier = optionalName.orElseGet(() -> "Default");
// ํจ์ํ ์คํ์ผ์ ์ฐ์ฐ
optionalName.map(String::toUpperCase)
.ifPresent(System.out::println); // ๊ฒฐ๊ณผ ์ถ๋ ฅ: JOHN
}
}
- Optional์ ์๋ฐ 8๋ถํฐ ๋์
๋ ๊ฐ์ ๊ฐ์ธ๊ณ ์๋ ๋ํผ ํด๋์ค๋ก, null์ ์์ ํ๊ฒ ์ฒ๋ฆฌํ๊ธฐ ์ํ ๊ธฐ๋ฅ์ ์ ๊ณตํฉ๋๋ค.
- null ๋์ ์ Optional.empty()๋ฅผ ์ฌ์ฉํ๋ฉฐ, NullPointException(NPE)๋ฅผ ๋ฐฉ์งํฉ๋๋ค.
- isEmpty() ๋๋ IsPresent() ๋ฉ์๋๋ฅผ ์ฌ์ฉํ์ฌ Optional์ด ๊ฐ์ ๊ฐ์ก๋์ง ํ์ธํ ์ ์์ต๋๋ค.
- get()๋ฉ์๋๋ฅผ ์ฌ์ฉํ๋ฉด Optional์ด ๊ฐ์ธ๊ณ ์๋ ๊ฐ์ ๊ฐ์ ธ์ฌ ์ ์์ง๋ง, ๊ฐ์ด ์๋ ๊ฒฝ์ฐ NoSuchElementException์ด ๋ฐ์ํ๋ฏ๋ก ๋จผ์ ๊ฐ์ด ์๋์ง ํ์ธํด์ผ ํฉ๋๋ค.
- Optional์ ๊ฐ์ด ์์ ๋ OrElse()๋ orElseGet()๋ก ๊ธฐ๋ณธ๊ฐ์ ์ค์ ํ๊ฑฐ๋ orElseThrow()๋ก ์์ธ๋ฅผ ๋ฐ์์ํฌ ์ ์์ต๋๋ค.
- ๋งต(Map)์ด๋ ํํฐ(Filter) ๋ฑ์ ํจ์ํ ์คํ์ผ ์ฐ์ฐ์ ์ ๊ณตํฉ๋๋ค.