canuc80k1116·17/50

Đếm Một Trong Dãy Gấp Đôi

Nộp bài trên LQDOJ

Bài 11 · Divide and Conquer

Với số nguyên không âm , định nghĩa dãy nhị phân : - Nếu chỉ gồm phần tử . - Nếu , tiếp theo là , rồi lại .

Các vị trí đánh số từ . Cho , hãy đếm số phần tử bằng trong đoạn .

Input

  • Một dòng chứa .

Output

  • In số lượng bit .

Constraints

  • và .

Scoring

  • Subtask ( điểm): .
  • Subtask ( điểm): không có giới hạn bổ sung.

Example

Test 1

Input

5 2 6

Output

3

Giải thích: ; đoạn vị trí là , có ba bit .

Lời giải tóm tắt
  • Dãy F(n) gồm F(⌊n/2⌋), bit n mod 2, rồi F(⌊n/2⌋). Tổng số bit 1 trong toàn bộ F(n) đúng bằng n.
  • Tính pre(n,k): số bit 1 trong k vị trí đầu. Nếu lấy cả dãy, trả n; nếu chỉ lấy một phần, xác định vị trí cắt nằm ở nửa trái, bit giữa hay nửa phải.
  • Chỉ đệ quy vào nửa bị cắt; phần đã lấy trọn cộng ngay bằng ⌊n/2⌋. Kết quả cần tìm là pre(n,r) − pre(n,l−1).
  • Code hiện tại tính lại độ dài dãy ở mỗi mức nên mất O(log² n), ngăn xếp O(log n); không tạo dãy có kích thước rất lớn.