분할 정복의 접근 방식은 아래와 같다:
이를 이진 탐색에 적용해보면:
이진 탐색에서는 분할된 2개의 배열 중 1개의 배열만 취하므로, 해답 도출을 위해 답을 합치는 절차는 생략해도 된다.
fn bs_iteration(arr: &[i32], target: &i32) -> Option<usize> {
let length = arr.len();
let mut mid = length / 2;
let mut low = 0;
let mut high = length - 1;
let mut current = arr[mid];
while low <= high { match current.cmp(&target) {
// target과 current가 같을 경우
std::cmp::Ordering::Equal => return Some(mid),
// current가 target 좌측에 있을 경우 (low < current < target < high)
std::cmp::Ordering::Less => low = mid + 1,
// current가 target 우측에 있을 경우 (low < target < current < high)
std::cmp::Ordering::Greater => high = mid - 1,
}
mid = (low + high) / 2;
current = arr[mid];
}
// 탐색에 실패한 경우
return None;
}
let mut high = length - 1;
match current.cmp(&target) {
std::cmp::Ordering::Equal => return Some(mid),
std::cmp::Ordering::Less => low = mid + 1,
std::cmp::Ordering::Greater => high = mid - 1,
}
cmp()
함수는 기준이 함수를 부르는 변수인 것으로 보인다. 이 코드에서 Less의 의미는 함수를 부른 current
가 &target
에 비해 작은 경우를 의미하는 듯함.fn binary_search() -> Option<usize> {
// ...
return None;
}
Option
에 대해 아래와 같이 설명하고 있다:Type
Option
represents an optional value: everyOption
is eitherSome
and contains a value, orNone
, and does not.Option
types are very common in Rust code, as they have a number of uses:
(생략)...
- Return value for otherwise reporting simple errors, whereNone
is returned on error
fn bs_recursion(arr: &[i32], target: i32, low: usize, high: usize) -> Option<usize> {
let mid = (low + high) / 2;
let current = arr[mid];
if low > high {
return None;
} else {
match current.cmp(&target) {
std::cmp::Ordering::Equal => return Some(mid),
std::cmp::Ordering::Less => bn_recursion(&arr, target, mid + 1, high),
std::cmp::Ordering::Greater => bn_recursion(&arr, target, low, mid - 1)
}
}
}
std::cmp::Ordering
에서 제공하는 항목이 Less
, Greater
, Equal
이렇게 셋 뿐이다. 이상이나 이하에 대한 표현이 없다는 말. 원래는 조건문을 쓰지 않고 low.cmp(&high)
로 'Rusty'하게 코드를 짜 보려고 했는데, Ordering
으로는 이상과 이하를 표현할 수 없다는 걸 알고 다시 조건문으로 돌아왔다. def binary_search_iteration(arr: list, target: int) -> int:
low = 0
high = len(arr)
mid = (low + high) // 2
if (low > high): return -1
else:
while (True):
if (target == arr[mid]): return mid
elif (target < arr[mid]): high = mid - 1
else: low = mid + 1
mid = (low + high) // 2
def binary_search_recursion(arr: list, target: int, low: int, high: int) -> int:
mid = (low + high) // 2
if (low > high): return -1
else:
if (target == arr[mid]): return mid
elif (target < arr[mid]): return binary_search_recursion(arr, target, low, mid - 1)
else: return binary_search_recursion(arr, target, mid + 1, high)
파이썬은 진짜 쉽다... Rust 붙잡고 있다간 내 성적이 날아갈 거 같아서 일단 Python으로 달리고, 시간 날 때나 좀 공부해보자.