Fibonacci
binary representation
bit counting
number systems
mathematical algorithms

Counting the bits set in the Fibonacci number system?

Master System Design with Codemia

Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.

Introduction

In the Fibonacci number system, a number is written as a sum of Fibonacci numbers rather than powers of two. The “bits set” in that representation are simply the Fibonacci terms that appear in the Zeckendorf decomposition. So counting the set bits means finding how many Fibonacci numbers are used in the unique valid representation of the integer.

What the Fibonacci Number System Means

The relevant representation here is usually the Zeckendorf representation. Every positive integer can be written uniquely as a sum of nonconsecutive Fibonacci numbers.

For example:

text
17 = 13 + 3 + 1

Using Fibonacci numbers 1, 2, 3, 5, 8, 13, ..., the fibinary-style representation of 17 contains three 1 bits because three Fibonacci terms are used.

This is similar in spirit to binary popcount, except the place values are Fibonacci numbers rather than powers of two.

The Greedy Algorithm

The standard way to build the Zeckendorf representation is greedy:

  1. find the largest Fibonacci number less than or equal to n
  2. subtract it
  3. repeat on the remainder
  4. count how many terms were chosen

This works because the greedy method produces the unique valid representation with no consecutive Fibonacci terms.

Python Implementation

python
1def fibonacci_up_to(n: int):
2    fibs = [1, 2]
3    while fibs[-1] <= n:
4        fibs.append(fibs[-1] + fibs[-2])
5    return fibs[:-1]
6
7
8def fib_popcount(n: int) -> int:
9    if n <= 0:
10        return 0
11
12    fibs = fibonacci_up_to(n)
13    count = 0
14    remaining = n
15
16    for f in reversed(fibs):
17        if f <= remaining:
18            remaining -= f
19            count += 1
20        if remaining == 0:
21            break
22
23    return count
24
25
26print(fib_popcount(17))
27print(fib_popcount(100))

For 17, the function returns 3, corresponding to 13 + 3 + 1.

Why the Greedy Method Is Enough

You do not need dynamic programming just to count the set bits for a single number. The greedy algorithm is enough because Zeckendorf’s theorem guarantees that choosing the largest possible Fibonacci term first leads to the unique valid decomposition.

That means counting the chosen terms during the greedy process gives the answer directly.

This is much simpler than generating all valid fibinary strings or attempting a recursive search.

If the Input Is Already a Fibinary String

Sometimes the problem is not “given an integer, find the count,” but “given a Fibonacci-system bit string, count how many ones it contains.”

If the string is already guaranteed to be a valid Fibonacci representation, the answer is simply:

python
1def count_ones(fibinary: str) -> int:
2    return fibinary.count("1")
3
4print(count_ones("100101"))

The hard part only exists when you start from the decimal integer and must derive the Fibonacci representation first.

Time Complexity

The greedy method is efficient.

  • generating Fibonacci numbers up to n takes O(k) time, where k is the number of Fibonacci terms up to n
  • scanning them in reverse also takes O(k)

Since k grows only logarithmically with n, this is quite fast in practice.

So for one input number, the algorithm is effectively lightweight.

A Small Walkthrough

Let us compute the fibinary popcount of 17.

Fibonacci terms up to 17 are:

text
1, 2, 3, 5, 8, 13

Greedy steps:

  • choose 13, remainder 4, count 1
  • skip 8 and 5
  • choose 3, remainder 1, count 2
  • choose 1, remainder 0, count 3

So the number of set bits is 3.

That is exactly analogous to popcount in binary, except the weights differ.

When the Problem Gets Harder

More advanced variants ask for things like:

  • the total number of Fibonacci-set bits in all numbers up to n
  • counting representations under extra constraints
  • working with very large n efficiently across many queries

Those versions may use dynamic programming, combinatorics, or matrix methods. But for the direct question “how many bits are set in the Fibonacci representation of this integer,” greedy is the right starting point.

Common Pitfalls

The biggest pitfall is using the standard Fibonacci sequence starting with 1, 1, 2, 3, ... without clarifying representation rules. Many fibinary implementations use place values 1, 2, 3, 5, ... to avoid duplicate representations.

Another issue is forgetting that valid Zeckendorf representations do not use consecutive Fibonacci terms.

Developers also sometimes overcomplicate the problem with exhaustive search when the greedy method already gives the unique answer.

Finally, if the input is already a fibinary string, do not recompute the whole decomposition unnecessarily. Just count the 1 characters.

Summary

  • In the Fibonacci number system, set bits correspond to the Fibonacci terms used in the Zeckendorf decomposition.
  • The greedy algorithm finds that decomposition efficiently.
  • Counting chosen terms during the greedy subtraction gives the fibinary popcount.
  • If the input is already a valid fibinary string, just count the 1 characters.
  • Be clear about which Fibonacci-place convention you are using before implementing the algorithm.

Course illustration
Course illustration

All Rights Reserved.