Files
enok/tests/referansebygg.rs
T
blandClaude Opus 5 a5185ccc5b
test / test (push) Failing after 4s
Knytt grensen for vinduslufting til normert settpunkt for kjøling
Grensen var satt til 24 °C uten kilde. NS 3031 gir en normert settpunkttemperatur
for kjøling også for bygninger uten kjøleanlegg, der overskuddsvarmen antas luftet
ut uten at energien telles. Den verdien er et bedre begrunnet utgangspunkt, og gir
mindre urealistisk lagring av solvarme i tette bygninger med store vindusflater.

Romoppvarmingen for TEK17-referansebygget går fra 24,7 til 27,2 kWh/(m²·år).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_015GeH3y8fwTaTudaD88P57o
2026-09-14 18:05:16 +02:00

100 lines
3.8 KiB
Rust
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
//! Kontroll mot Standard Norges lanseringseksempel for NS 3031:2025 (Multiconsult, mai 2025):
//! småhus med TEK17-standard i Oslo-klima.
//!
//! Eksempelet er beregnet med Simien 8. Varmetapsbudsjettet og de normerte energipostene
//! gjengis her nøyaktig. Romoppvarmingen avviker, se kommentaren nederst i filen.
use enok::data::Datakilde;
use enok::inndata;
use enok::kjor;
use std::path::Path;
fn kjor_referansebygg() -> kjor::Resultat {
let b = inndata::les_bygning(Path::new("eksempler/tek17-smaahus.toml")).unwrap();
kjor::kjor(&b, &Datakilde::default()).unwrap()
}
fn post(r: &kjor::Resultat, nr: &str) -> f64 {
let p = r.budsjett.poster.iter().find(|p| p.nr == nr).unwrap();
p.netto / r.lost.bra
}
fn naer(faktisk: f64, forventet: f64, toleranse: f64, hva: &str) {
assert!(
(faktisk - forventet).abs() <= toleranse,
"{hva}: beregnet {faktisk:.2}, forventet {forventet:.2} (toleranse {toleranse})"
);
}
/// Varmetapsbudsjettet skal gjengi NS 3031:2025 Tabell 3 for TEK17-referansebygget.
#[test]
fn varmetapsbudsjett_som_publisert() {
let r = kjor_referansebygg();
let v = &r.varmetap;
naer(v.vegger, 0.22, 0.005, "vegger");
naer(v.tak, 0.07, 0.005, "tak");
naer(v.gulv, 0.05, 0.005, "gulv");
naer(v.vinduer_dorer, 0.20, 0.005, "vinduer og dører");
naer(v.kuldebroer, 0.05, 0.005, "kuldebroer");
naer(v.transmisjon, 0.59, 0.005, "transmisjon");
naer(v.infiltrasjon, 0.04, 0.005, "infiltrasjon");
naer(v.klimaskjerm, 0.63, 0.005, "klimaskjerm");
naer(v.ventilasjon, 0.06, 0.005, "ventilasjon");
naer(v.totalt, 0.69, 0.005, "totalt varmetapstall");
}
/// De normerte energipostene skal treffe verdiene i NS 3031:2025 Tillegg A for småhus.
#[test]
fn normerte_energiposter_som_publisert() {
let r = kjor_referansebygg();
naer(post(&r, "2"), 25.1, 0.2, "varmtvann");
naer(post(&r, "5"), 11.4, 0.2, "belysning");
naer(post(&r, "6"), 17.5, 0.2, "teknisk utstyr");
naer(post(&r, "3a"), 0.0, 0.01, "romkjøling");
naer(post(&r, "3b"), 0.0, 0.01, "ventilasjonskjøling");
}
/// Energikarakteren for et TEK17-bygg skal være B, jf. energimerkeforskriften § 10b.
#[test]
fn tek17_bygg_faar_karakter_b_eller_bedre() {
let r = kjor_referansebygg();
assert!(
matches!(r.karakter.bokstav, "A" | "B"),
"TEK17-referansebygget fikk karakter {}, forventet A eller B",
r.karakter.bokstav
);
}
/// Regresjonsvakt for romoppvarming og samlet netto energibehov.
///
/// Det publiserte eksempelet oppgir 46,2 kWh/(m²·år) romoppvarming og 106,4 kWh/(m²·år)
/// netto energibehov. enok beregner vesentlig lavere romoppvarming. Kontrollene som er gjort:
///
/// * solinnstrålingen på skrå og orienterte flater er sammenlignet med pvlib (HayDavies) og
/// avviker under 1 % for alle himmelretninger i Oslo-klima;
/// * varmetapet i stasjonær tilstand stemmer med U·A·ΔT innenfor 2 % (se `tests/motor.rs`);
/// * årlig energibalanse går opp innenfor 2 %;
/// * varmetapsbudsjettet og de normerte energipostene er identiske med de publiserte.
///
/// Avviket ligger dermed i hvor stor del av solvarmen som nyttiggjøres. NS 3031:2025 Tillegg A
/// er ikke offentlig tilgjengelig, så de normerte solfaktorene, skjermingsforutsetningene og
/// timesprofilene som Simien 8 bruker, lar seg ikke etterprøve her. Testen låser dagens verdier
/// slik at endringer i motoren blir synlige, og oppdateres når standardens forutsetninger er
/// tilgjengelige.
#[test]
fn regresjonsvakt_for_romoppvarming() {
let r = kjor_referansebygg();
naer(
post(&r, "1a"),
27.2,
1.5,
"romoppvarming (regresjon, publisert verdi 46,2)",
);
naer(
r.budsjett.netto_spesifikk(r.lost.bra),
86.7,
2.0,
"netto energibehov (regresjon, publisert verdi 106,4)",
);
}