reduceLogSumExp reference decomposition contradicts conformance test; accuracy requirements missing
Nessuno ha ancora preso questa issue.
Valutazione
- Difficoltà
- 4/5
- Tempo stimato
- 1-2 giorni
- Idoneità per principianti
- 22/100
- Tipo di issue
- Bug
- Chiarezza
- Abbastanza chiara
- Stato di attività
- Tranquilla
- Stack tecnologico
- bash, javascript
- Ambito
- documentation, machine-learning
Direzione di ricerca
The normative reference decomposition for reduceLogSumExp sits in the reduction operations section of the WebNN spec source (Bikeshed), and the conformance case is in web-platform-tests at webnn/conformance_tests/reduce_log_sum_exp.https.any.js near line 1304. Read both, then confirm the overflow by tracing exp(100.0) in float32. Done means the spec's decomposition is changed to a max-shifted form that passes that test, with the accuracy wording agreed by maintainers in the thread.
Scritto dal modello di indicizzazione a partire dal testo della issue.
Descrizione
Summary
The spec’s reference algorithm for reduceLogSumExp overflows for inputs that the conformance tests expect to succeed. Additionally, the spec does not define any accuracy or numerical stability requirements for this operation, making it unclear what a conformant implementation must do.
The contradiction
The spec defines reduceLogSumExp with this reference decomposition:
function reduceLogSumExp(builder, input, options) {
return builder.log(builder.reduceSum(builder.exp(input), options));
}
However, the conformance tests include:
{
'name': 'reduceLogSumExp avoids overflows caused by taking the exp of large inputs',
'graph': {
'inputs': {
'reduceLogSumExpInput': {
'data': [100.0],
'descriptor': {shape: [1], dataType: 'float32'}
}
},
'operators': [{
'name': 'reduceLogSumExp',
'arguments': [
{'input': 'reduceLogSumExpInput'},
{'options': {'axes': [0], 'keepDimensions': false}}
],
'outputs': 'reduceLogSumExpOutput'
}],
'expectedOutputs': {
'reduceLogSumExpOutput': {
'data': [100.0],
'descriptor': {shape: [], dataType: 'float32'}
}
}
}
}
Tracing through the reference decomposition with this input:
exp(100.0) ≈ 2.69 × 10⁴³ → overflows float32 (max ≈ 3.40 × 10³⁸) → +inf
reduceSum([+inf]) → +inf
log(+inf) → +inf
Expected result: 100.0
Actual result from reference algorithm: +inf
The test name even acknowledges the issue (“avoids overflows caused by taking the exp of large inputs”), yet the normative algorithm does not avoid it.
Root cause
The log-sum-exp operation is numerically stable only when computed using the well-known max-subtraction trick:
reduceLogSumExp(x, axes) = max + log(sum(exp(x - max)))
where max = reduceMax(x, axes). This works because the outer log algebraically absorbs the exp(max) factor. Without the log wrapper (i.e., for plain reduceSum(exp(x))), no such trick is possible. The overflow is inherent to the result.
The entire purpose of reduceLogSumExp existing as a fused operation (rather than being decomposed by the user) is to enable this stable computation. The current spec text undermines that purpose.
Proposed fix
Replace the reference decomposition with the numerically stable formulation:
function reduceLogSumExp(builder, input, options) {
const max = builder.reduceMax(input, { ...options, keepDimensions: true });
const shifted = builder.sub(input, max);
const sumExp = builder.reduceSum(builder.exp(shifted), options);
const maxSqueezed = builder.reduceMax(input, options); // without keepDims
return builder.add(maxSqueezed, builder.log(sumExp));
}
Add normative text stating that implementations must compute reduceLogSumExp using a numerically stable algorithm, or at minimum specify accuracy bounds, e.g., the result must not overflow for any input where the mathematically exact result is representable in the output data type.
Additional concern: underspecified accuracy for reductions generally
The broader reduction operations section does not specify accuracy requirements for any reduction op. For reduceLogSumExp specifically, this means an implementation that naively follows the decomposition and returns +inf for exp(89) inputs is technically spec-conformant — but fails the conformance tests. The spec should be clear about what it expects.
- Lingua principale
- Bikeshed
- Stelle
- 566
- Fork
- 72
- Merge medio
- 6g 5h
- PR unite (30g)
- 1
Preparare l'ambiente
- Nessun Dockerfile né file Docker Compose
- Nessun modello di pull request
- Leggi la guida per i contributori
Come iniziare
- Leggi tutta la issue e poi la guida ai contributi del progetto.
- Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
- Fai un fork del repository e lavora su un branch.
- Apri una pull request che faccia riferimento al numero della issue.
Altre issue di webmachinelearning/webnn
-
Difficoltà 5/5 Più di una settimana Idoneità per principianti 25/100
webmachinelearning/webnn#966 ·
-
Difficoltà 5/5 Più di una settimana Idoneità per principianti 35/100
webmachinelearning/webnn#965 ·
-
Difficoltà 3/5 1-2 giorni Idoneità per principianti 68/100
webmachinelearning/webnn#964 · 1 commento ·
-
Difficoltà 5/5 Più di una settimana Idoneità per principianti 30/100
webmachinelearning/webnn#963 · 1 commento · 1 reazione ·
-
Difficoltà 5/5 Più di una settimana Idoneità per principianti 8/100
webmachinelearning/webnn#961 ·
Tutte le issue di webmachinelearning/webnn
Issue simili
-
Difficoltà 1/5 Meno di un'ora Idoneità per principianti 78/100
-
beginner-friendly category:fixtures community enhancement first-timers-only good first issue hacktoberfest help wanted low hanging fruit micro-contribution type: task up-for-grabs
Difficoltà 1/5 Meno di un'ora Idoneità per principianti 85/100
Berserk-hub150/skillhawk#229 · 1 commento ·
I maintainer di solito rispondono entro 8 giorni
-
changelog investigate
Difficoltà 2/5 1-3 ore Idoneità per principianti 65/100
ramnes/notion-sdk-py#423 ·
-
ready-for-agent
Difficoltà 2/5 1-3 ore Idoneità per principianti 77/100
I maintainer di solito rispondono entro 1 giorno
-
Difficoltà 1/5 1-3 ore Idoneità per principianti 89/100
duckdb/duckdb-web#7514 ·
I maintainer di solito rispondono entro 1 giorno