Excel 16.0 build 20430
Windows, 64-bit, CPU not recorded
61,630 captured inputs are indexed for this environment. Capture dates: 2026-09-29 to 2026-09-29. This is a reading count, not a comparison with another build.
Financial functions
Matches all 1,770 recorded answers
Recorded: 1,761 in the answer bank and 9 workbook cells. How we measure this · See the Rust code
| Language | Name in Excel |
|---|---|
| Arabic | DDB |
| Bulgarian | DDB |
| Czech | ODPIS.ZRYCH2 |
| Danish | DSA |
| German | DDB |
| Greek | DDB |
| English (Australia) | DDB |
| English (United Kingdom) | DDB |
| English (United States) | DDB |
| Spanish | DDB |
| Estonian | DDB |
| Finnish | DDB |
| French | DDB |
| Hebrew | DDB |
| Croatian | DDB |
| Hungarian | KCSA |
| Indonesian | DDB |
| Italian | DDB |
| Japanese | DDB |
| Korean | DDB |
| Lithuanian | DDB |
| Latvian | DDB |
| Norwegian | DDB |
| Dutch | DDB |
| Polish | DDB |
| Portuguese (Brazil) | DDB |
| Portuguese (Portugal) | BDD |
| Romanian | DDB |
| Russian | ДДОБ |
| Slovak | DDB |
| Slovenian | DDB |
| Serbian (Latin) | DDB |
| Swedish | DEGAVSKR |
| Thai | DDB |
| Turkish | ÇİFTAZALANBAKİYE işlevi |
| Ukrainian | DDB |
| Vietnamese | DDB |
| Chinese (Simplified) | DDB |
| Chinese (Hong Kong) | DDB |
| Chinese (Traditional) | DDB |
Names from Microsoft's support site.
DDB(cost, salvage, life, period, [factor])
DDB(cost, salvage, life, period, [factor]) returns the depreciation charge for one period
under the double-declining-balance method, or any other declining rate you name.
Microsoft's Learn page gives the rule in one line:
Min( (cost − total depreciation from prior periods) × (factor / life), (cost − salvage − total depreciation from prior periods) )
Writing book for cost minus the depreciation already taken, that is:
charge = min( book × factor / life, book − salvage )
The first term is the declining-balance charge: a constant fraction factor/life of the
remaining book value. With the default factor = 2 that fraction is twice the straight-line
rate, which is where "double declining" comes from — the method writes off twice as fast at the
start and tapers.
The second term is a clamp: the charge may never take the book value below salvage.
Two properties define the method, and both matter:
salvage, DDB applies whatever factor/life you specify and lets the
clamp deal with the consequences.salvage enters only through the clamp. It does not affect the declining-balance term at
all, so for early periods DDB returns the same number whatever salvage is.DDB(cost, salvage, life, period, [factor])
| Argument | Meaning (Microsoft's wording) | Required? |
|---|---|---|
cost | "The initial cost of the asset." | Required |
salvage | "The value at the end of the depreciation … This value can be 0." | Required |
life | "The number of periods over which the asset is being depreciated." | Required |
period | "The period for which you want to calculate the depreciation. Period must use the same units as life." | Required |
factor | "The rate at which the balance declines. If factor is omitted, it is assumed to be 2 (the double-declining balance method)." | Optional, defaults to 2 |
period is 1-based, like DB and unlike the French pair
AMORLINC / AMORDEGRC.
period and life must be in the same units. Monthly depreciation of a five-year asset
means life = 60 and period in months — and factor/life shrinks accordingly, which is the
point.
Numeric slots follow the shared model; see Coercion and lifting.
Declining balance has a well-known defect: book × factor/life shrinks geometrically and never
reaches zero, so the asset is never fully written off within its life. Standard accounting
practice is to switch to straight line for the remaining periods once straight line would
give the larger charge.
DDB does not do that. Microsoft is explicit: "Use the VDB function if you want to switch to
the straight-line depreciation method when depreciation is greater than the declining balance
calculation." DDB runs pure declining balance, clamped at salvage, for the whole life.
So a DDB schedule summed over 1 … life does not generally reach cost − salvage. It
approaches it geometrically and stops short — unless the clamp cuts in near the end, which
happens only when salvage is large enough for the geometric tail to reach it. This is the
single most common surprise in the depreciation category, and it is documented behaviour, not a
defect.
The comparison that makes the family legible:
| rate | salvage used for | switches to straight line | first-period proration | |
|---|---|---|---|---|
SLN | implicit, flat | the whole charge | n/a | none |
| DB | derived from the salvage ratio, rounded to 3 dp | deriving the rate | no | month |
DDB | factor / life, supplied | a clamp only | no | none |
VDB | factor / life, supplied | a clamp only | optional | period range |
SYD | implicit, declining | the whole charge | n/a | none |
Returns a Number: the charge for the requested period, in the units of cost.
salvage is invisible early. For any period where book × factor/life is below
book − salvage, the answer does not depend on salvage at all. A spreadsheet in which
changing salvage changes nothing is behaving correctly.salvage, every later
period returns 0 rather than an error.factor > life makes factor/life exceed 1, so the first period would write off more
than the whole asset; the clamp reduces it to cost − salvage. Nothing in the documentation
forbids it.life is accepted; the final partial period is shorter than 1 and its charge is
prorated accordingly.cost − salvage, per the section above. This is not an edge
case; it is the normal outcome.Microsoft's Learn page documents no error values and no error conditions — only the "all five arguments must be positive numbers" remark, which is contradicted on the same page.
min and therefore a branch. Near the crossover the two terms are close,
and which one wins is decided by a floating-point comparison. Two implementations that agree
on both terms to the last bit can still disagree on the answer at exactly one period.factor / life is one division, not a per-period recomputation. Forming it once and
multiplying is not the same as multiplying by factor and dividing by life each period;
pin the choice.DDB is
multiplication, subtraction and comparison throughout. It is the most numerically
straightforward member of the family — which makes it a good calibration surface for a future
vector suite, since any disagreement is semantic rather than about a library pow.VDB interval logic on a unit interval, which is a defensible reading and is not the only
one.Quoted from the public repository DnaCalc/DnaCalc, crates calc-func and calc-fml, at commit 9e1884369a67. Comments are the source's own. A kernel shared with other functions appears once, on its module page.
DDB · 5 lines · calc-func/src/catalogue/financial.rs on GitHub24 ddb_fn "DDB" (4, 5) [V "cost", V "salvage", V "life", V "period", V "factor"] |s, a, sv| {
let (cost, salvage, life, period) = (num(s, a, 0)?, num(s, a, 1)?, num(s, a, 2)?, num(s, a, 3)?);
let factor = if a.len() > 4 { num(s, a, 4)? } else { 2.0 };
out(s, dep::ddb_kernel(cost, salvage, life, period, factor))
}
ddb_kernel · 14 lines · calc-func/src/ported/depreciation_family.rs on GitHubpub fn ddb_kernel(
cost: f64,
salvage: f64,
life: f64,
period: f64,
factor: f64,
) -> Result<f64, WorksheetErrorCode> {
validate_finite(&[cost, salvage, life, period, factor])?;
if cost < 0.0 || salvage < 0.0 || life <= 0.0 || period <= 0.0 || period > life || factor <= 0.0
{
return Err(WorksheetErrorCode::Num);
}
ddb_period_depreciation(cost, salvage, life, period, factor)
}
validate_finite ported/depreciation_familypublish_depreciation ported/depreciation_familydepreciation_integer_power ported/depreciation_familyddb_period_depreciation ported/depreciation_familybackend::sqrt ported/excel_numericbinary_with ported/excel_numericexcel_pow_positive ported/excel_numericexcel_pow_chain ported/excel_numericexcel_x87_sub ported/excel_numericexcel_x87_mul ported/excel_numericexcel_x87_div ported/excel_numericexcel_x87_recip ported/excel_numericmul ported/excel_numeric/x87sub ported/excel_numeric/x87div ported/excel_numeric/x87recip ported/excel_numeric/x87pow2_positive ported/excel_numeric/x87_chainspow2 ported/excel_numeric/x87_chainsexp_ext ported/excel_numeric/x87_chainsexp_with ported/excel_numeric/x87_chainsexcel_exp ported/excel_numeric/x87_chainslog_with ported/excel_numeric/x87_chainsexcel_log ported/excel_numeric/x87_chainsexact_integer_magnitude ported/power_fnaccept_negative_base_odd_root ported/power_fnbinexp_positive ported/power_fnpower_kernel ported/power_fnNo implementation has been published with a Handbook test suite for this function.
The recorded environments below distinguish a reading from a same-input comparison. Counts describe captured inputs in each environment; overlapping captures and comparisons are not totals of unique worksheet calls.
| Excel 16.0 build | Platform and CPU | Captured inputs |
|---|---|---|
| 20430 | Windows, 64-bit, CPU not recorded | 61,630 |
The record contains no same-input comparison between these environments. Reading different inputs on different builds does not establish either a version change or cross-build agreement.
Recorded environments and comparison details.
Windows, 64-bit, CPU not recorded
61,630 captured inputs are indexed for this environment. Capture dates: 2026-09-29 to 2026-09-29. This is a reading count, not a comparison with another build.
month count. See the comparison table above.SLN — the straight-line charge (cost − salvage)/life. Comparing DDB against SLN
period by period is how you find where a switching method would switch, and therefore where
DDB starts under-charging relative to accounting practice.SYD — sum-of-years-digits: also accelerated, but it does exhaust cost − salvage
exactly.factor but is derived from rate and cannot be supplied, and its
last two periods are forced to 50 and 100 per cent. Not a substitute.VDB (above), and with the assumption that a DDB column sums to
cost − salvage.No named variants are recorded yet.
Suggest a correction or contribute an implementation · For agents