Solution#
Memo#
- 이분탐색 문제
- 뭔가 카테고리가 분류되지 않았다면 다른걸로 풀었을지도
- 정렬 후, 나는 높이의 인덱스가 부딪히지 않는 벽의 숫자가 된다. (그걸 길이에서 빼줌)
// Baekjoon - 3020
// https://www.acmicpc.net/problem/3020
use std::io::{self, Read, Write};
fn main() {
let mut stdin = io::stdin().lock();
let mut stdout = io::stdout().lock();
let mut input = String::new();
stdin.read_to_string(&mut input).unwrap();
let mut lines = input.lines();
let first_line = lines.next().unwrap();
let parts: Vec<usize> = first_line
.split_whitespace()
.map(|x| x.parse().unwrap())
.collect();
let n = parts[0];
let h = parts[1];
let mut bottom = Vec::with_capacity(n / 2);
let mut top = Vec::with_capacity(n / 2);
for i in 0..n {
let height: usize = lines.next().unwrap().parse().unwrap();
if i % 2 == 0 {
bottom.push(height);
} else {
top.push(height);
}
}
bottom.sort_unstable();
top.sort_unstable();
let mut min_obstacles = n;
let mut count = 0;
for fly_height in 1..=h {
let bottom_hits = bottom.len() - lower_bound(&bottom, fly_height);
let top_hits = top.len() - lower_bound(&top, h - fly_height + 1);
let total_hits = bottom_hits + top_hits;
if total_hits < min_obstacles {
min_obstacles = total_hits;
count = 1;
} else if total_hits == min_obstacles {
count += 1;
}
}
writeln!(stdout, "{} {}", min_obstacles, count).unwrap();
}
fn lower_bound(arr: &[usize], target: usize) -> usize {
let mut left = 0;
let mut right = arr.len();
while left < right {
let mid = (left + right) / 2;
if arr[mid] < target {
left = mid + 1;
} else {
right = mid;
}
}
left
}