Search topics...

How do you multiply without using multiply or divide instructions for a multiplier constant of 10, 31, 132?

0 upvotes
Practice with AISoon

Decompose each constant into sums/differences of power-of-two multiples, since multiplying by 2^k is a left shift (x << k). Choose the form with the fewest shift/add ops.

  • × 10 = 8x + 2x = (x << 3) + (x << 1)
  • × 31 = 32x − x = (x << 5) − x (one shift and one subtract — cheaper than the additive form)
  • × 132 = 128x + 4x = (x << 7) + (x << 2)
c
#include <stdint.h>
uint32_t mul10(uint32_t x) { return (x << 3) + (x << 1); }
uint32_t mul31(uint32_t x) { return (x << 5) - x; }
uint32_t mul132(uint32_t x) { return (x << 7) + (x << 2); }

Why this works: any constant has a binary expansion, so c * x = Σ (x << i) over the set bits i of c. Using subtraction lets you collapse runs of consecutive 1-bits (this is the idea behind canonical signed digit / Booth recoding): 31 = 0b11111, five set bits would be four adds, but 31 = 32 − 1 reduces it to one shift + one subtract.

Notes:

  • Compilers already do this ("strength reduction") for constant multipliers, so you rarely write it by hand except on MCUs lacking a hardware multiplier or in hand-tuned DSP code.
  • Watch for overflow: the intermediate x << 7 must fit in the chosen integer width; use uint32_t/uint64_t appropriately.
  • Division by a constant is also done without a divide instruction, but via a multiply-by-reciprocal-and-shift trick — not by shifts alone (only division by powers of two is a plain shift).