Binary Search
Binary Search란?

• 정렬된 시퀀스에서 빠르게 값을 찾는데 사용되는 알고리즘
  – 목표값을 검색공간의 중간값과 비교한다.
  – 목표값이 중간값보다 작으면 중간값의 왼쪽 서브시퀀스를, 중간값보다
    크면 오른쪽 서브시퀀스를 새로운 검색공간으로 한다.
  – 목표값을 찾을 때까지 이 과정을 반복한다.
Binary Search란?

Target value: 55

      z     5      13   19   22   41   55    68   72   81   98




                                       55    68   72   81   98

                                            원소의 개수가 짝수일 때 중간값은?

                                       55    68
Complexity

•   O(log N)
•   단, 시퀀스에 대한 Random access가 가능할 경우에 한함
Discrete Binary
    Search
• 배열을 인덱스를 해당 값에 사상하는 함수로 생각할 수 있음
• 배열이 정렬되어있다는 것은 단조함수(Monotonic function) 라는 것
  을 의미
• 따라서, 정의역이 정수 집합에 속하는 임의의 단조함수 f(x)에 대해
  이진 탐색을 적용하는 것이 가능
• 장점
  – 목표값을 찾기 위해 최대 O(log N)의 비교가 필요
  – 함수값을 그렇게 많이 계산할 필요없음
  – 배열과 달리 메모리에 제한을 받지 않음
Discrete Binary
    Search
• f(x) = x^8 + x^4 + x^2 + 1 (단조 증가 함수)
• 검색공간(정의역): 1~1024
• 목표값: 277
   –   f(512) > 277
   –   f(256) > 277
   –   f(128) > 277
   –   ...
   –   …
   –   f(4) > 277
   –   f(2) = 277
Main Theorem

• Predictate(술어) p: 검색 공간에 대해 Boolean 값을 반환하는 함수
  로 정의. EX) Is A[x] greater than or equal to the target value?
• Main theorem: 어떤 문제의 해를 찾을 때, 모든 y>x에 대해 p(x)를
  통해 p(y)의 값을 추정할 수 있다면 이진 탐색을 사용할 수 있다.
• EX) p(x)가 true인 가장 작은 x를 찾아라
   – 검색 공간이 이미 정렬되어 있다면 Main theorem을 만족하므로 이직 탐색 적용
     가능
   – p(x)가 true인 첫번째 x가 답
Main Theorem

• 특정한 값을 탐색하는 형태로는 모델링할 수 없지만 어
  떤 predictate를 정의하고 이를 평가하는 방식으로 바꿔
  서 풀 수 있는 문제들이 많음
SRM 169
Division1 Level2
• 일렬로 늘어선 캐비닛이 있고 각 캐비닛 안에 있는 폴더의 개수가
  배열로 주어져 있을 때, N 명의 직원으로 특정한 폴더를 찾고자 한
  다. 늘어선 캐비닛을 N개의 섹션으로 나누고(각 섹션의 캐비닛의
  개수가 같을 필요는 없다.) 각 직원이 자신의 섹션에 그 폴더가 있는
  지 찾게 할 때, 한 직원이 뒤져야 하는 폴더의 최대 개수의 최소값을
  구하여라. 단, 캐비닛은 안에 들어있는 폴더의 개수로 정렬되어 있
  다.
• EX)
  –   {10, 20, 30, 40, 50, 60, 70, 80, 90}
  –   직원 수: 3
  –   10 20 30 40 50 | 60 70 | 80 90
  –   return 170
SRM 169
Division1 Level2
• 한 직원이 뒤져야 하는 폴더의 최대 개수가 MAX로 주어질 때 필요
  한 직원의 수를 구하면?
• 앞의 문제는 결국 필요한 직원의 수가 이용할 수 있는 직원의 수(N)
  보다 작거나 같을 때, MAX의 최소값을 구하는 문제
  – Predicate p: 이용할 수 있는 직원의 수가 주어질 때, 각 직원들이 담당해야 하는
    폴더의 최대 개수가 x가 되도록 섹션을 나눌 수 있는가?
     •   필요한 직원의 수와 x는 반비례(단조 감소)
     •   low 의 초기값: 캐비닛에 들어있는 폴더의 최대 개수
     •   High의 초기값: 폴더 개수의 총 합
            – x = (low + high)
            – 필요한 직원의 수가 이용할 수 있는 직원의 수보다 크면 x를 증가(low = x + 1)
            – 아니면 x를 감소(hi = x)
            – 필요한 직원의 수와 이용 가능한 직원의 수가 같은 최소의 x를 찾을 때까지(low == high) 이 과
               정을 반복
SRM 169
Division1 Level2
int getMostWork( vector<int> folders, int workers ) {
  int n = folders.size();
  int lo = *max_element( folders.begin(), folders.end() );
  int hi = accumulate( folders.begin(), folders.end(), 0 );

    while ( lo < hi ) {
      int x = lo + (hi-lo)/2;
      int required = 1, current_load = 0;
      for ( int i=0; i<n; ++i ) {
         if ( current_load + folders[i] <= x ) {
            // the current worker can handle it
            current_load += folders[i];
         }
         else {
            // assign next worker
            ++required;
            current_load = folders[i];
         }
      }
      if ( required <= workers )
         hi = x;
      else
         lo = x+1;
    }
    return lo;
}
Binary Search in
      STL
•   bool binary_search (ForwardIterator beg, ForwardIterator end, const T& value)

•   ForwardIterator upper_bound (ForwardIterator beg, ForwardIterator end, const T& value)

•   ForwardIterator lower_bound (ForwardIterator beg, ForwardIterator end, const T& value)

•   pair<ForwardIterator,ForwardIterator> equal_range (ForwardIterator beg, ForwardIterator end,
    const T& value)

Binary Search

  • 1.
  • 2.
    Binary Search란? • 정렬된시퀀스에서 빠르게 값을 찾는데 사용되는 알고리즘 – 목표값을 검색공간의 중간값과 비교한다. – 목표값이 중간값보다 작으면 중간값의 왼쪽 서브시퀀스를, 중간값보다 크면 오른쪽 서브시퀀스를 새로운 검색공간으로 한다. – 목표값을 찾을 때까지 이 과정을 반복한다.
  • 3.
    Binary Search란? Target value:55 z 5 13 19 22 41 55 68 72 81 98 55 68 72 81 98 원소의 개수가 짝수일 때 중간값은? 55 68
  • 4.
    Complexity • O(log N) • 단, 시퀀스에 대한 Random access가 가능할 경우에 한함
  • 5.
    Discrete Binary Search • 배열을 인덱스를 해당 값에 사상하는 함수로 생각할 수 있음 • 배열이 정렬되어있다는 것은 단조함수(Monotonic function) 라는 것 을 의미 • 따라서, 정의역이 정수 집합에 속하는 임의의 단조함수 f(x)에 대해 이진 탐색을 적용하는 것이 가능 • 장점 – 목표값을 찾기 위해 최대 O(log N)의 비교가 필요 – 함수값을 그렇게 많이 계산할 필요없음 – 배열과 달리 메모리에 제한을 받지 않음
  • 6.
    Discrete Binary Search • f(x) = x^8 + x^4 + x^2 + 1 (단조 증가 함수) • 검색공간(정의역): 1~1024 • 목표값: 277 – f(512) > 277 – f(256) > 277 – f(128) > 277 – ... – … – f(4) > 277 – f(2) = 277
  • 7.
    Main Theorem • Predictate(술어)p: 검색 공간에 대해 Boolean 값을 반환하는 함수 로 정의. EX) Is A[x] greater than or equal to the target value? • Main theorem: 어떤 문제의 해를 찾을 때, 모든 y>x에 대해 p(x)를 통해 p(y)의 값을 추정할 수 있다면 이진 탐색을 사용할 수 있다. • EX) p(x)가 true인 가장 작은 x를 찾아라 – 검색 공간이 이미 정렬되어 있다면 Main theorem을 만족하므로 이직 탐색 적용 가능 – p(x)가 true인 첫번째 x가 답
  • 8.
    Main Theorem • 특정한값을 탐색하는 형태로는 모델링할 수 없지만 어 떤 predictate를 정의하고 이를 평가하는 방식으로 바꿔 서 풀 수 있는 문제들이 많음
  • 9.
    SRM 169 Division1 Level2 •일렬로 늘어선 캐비닛이 있고 각 캐비닛 안에 있는 폴더의 개수가 배열로 주어져 있을 때, N 명의 직원으로 특정한 폴더를 찾고자 한 다. 늘어선 캐비닛을 N개의 섹션으로 나누고(각 섹션의 캐비닛의 개수가 같을 필요는 없다.) 각 직원이 자신의 섹션에 그 폴더가 있는 지 찾게 할 때, 한 직원이 뒤져야 하는 폴더의 최대 개수의 최소값을 구하여라. 단, 캐비닛은 안에 들어있는 폴더의 개수로 정렬되어 있 다. • EX) – {10, 20, 30, 40, 50, 60, 70, 80, 90} – 직원 수: 3 – 10 20 30 40 50 | 60 70 | 80 90 – return 170
  • 10.
    SRM 169 Division1 Level2 •한 직원이 뒤져야 하는 폴더의 최대 개수가 MAX로 주어질 때 필요 한 직원의 수를 구하면? • 앞의 문제는 결국 필요한 직원의 수가 이용할 수 있는 직원의 수(N) 보다 작거나 같을 때, MAX의 최소값을 구하는 문제 – Predicate p: 이용할 수 있는 직원의 수가 주어질 때, 각 직원들이 담당해야 하는 폴더의 최대 개수가 x가 되도록 섹션을 나눌 수 있는가? • 필요한 직원의 수와 x는 반비례(단조 감소) • low 의 초기값: 캐비닛에 들어있는 폴더의 최대 개수 • High의 초기값: 폴더 개수의 총 합 – x = (low + high) – 필요한 직원의 수가 이용할 수 있는 직원의 수보다 크면 x를 증가(low = x + 1) – 아니면 x를 감소(hi = x) – 필요한 직원의 수와 이용 가능한 직원의 수가 같은 최소의 x를 찾을 때까지(low == high) 이 과 정을 반복
  • 11.
    SRM 169 Division1 Level2 intgetMostWork( vector<int> folders, int workers ) { int n = folders.size(); int lo = *max_element( folders.begin(), folders.end() ); int hi = accumulate( folders.begin(), folders.end(), 0 ); while ( lo < hi ) { int x = lo + (hi-lo)/2; int required = 1, current_load = 0; for ( int i=0; i<n; ++i ) { if ( current_load + folders[i] <= x ) { // the current worker can handle it current_load += folders[i]; } else { // assign next worker ++required; current_load = folders[i]; } } if ( required <= workers ) hi = x; else lo = x+1; } return lo; }
  • 12.
    Binary Search in STL • bool binary_search (ForwardIterator beg, ForwardIterator end, const T& value) • ForwardIterator upper_bound (ForwardIterator beg, ForwardIterator end, const T& value) • ForwardIterator lower_bound (ForwardIterator beg, ForwardIterator end, const T& value) • pair<ForwardIterator,ForwardIterator> equal_range (ForwardIterator beg, ForwardIterator end, const T& value)