Legg til barnehage, kontor-, skole-, idretts- og kulturbygg
Driftstidene har nå dager per uke og uker per år, og lastene gjelder bare på driftsdager. Normerte verdier for de nye kategoriene er hentet fra publiserte Simien-utskrifter og DiBK-utredninger og kontrollert mot energibudsjettene i de samme kildene. Boligblokk har fått egne verdier i stedet for en kopi av småhus. Balanserte anlegg kan ha kjølebatteri, og varmegjenvinneren reguleres ned når den ellers ville varmet tilluften over settpunktet. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_015GeH3y8fwTaTudaD88P57o
This commit is contained in:
@@ -0,0 +1,143 @@
|
||||
//! Kontroll av de normerte inndataene for yrkesbyggkategoriene: driftsdager, faste energiposter
|
||||
//! og kjølebatteri.
|
||||
|
||||
use enok::data::Datakilde;
|
||||
use enok::kjor;
|
||||
use enok::modell::{Bygning, Kategori};
|
||||
|
||||
fn prøvebygg(kategori: &str, kjolebatteri: bool) -> Bygning {
|
||||
let s = format!(
|
||||
r#"
|
||||
[bygning]
|
||||
navn = "Prøvebygg"
|
||||
kategori = "{kategori}"
|
||||
byggeaar = 2020
|
||||
oppvarmet_bra = 1200.0
|
||||
oppvarmet_volum = 3840.0
|
||||
|
||||
[klima]
|
||||
kommune = "Oslo"
|
||||
|
||||
[[flate]]
|
||||
navn = "Vegger"
|
||||
type = "vegg"
|
||||
areal = 560.0
|
||||
u_verdi = 0.18
|
||||
|
||||
[[flate]]
|
||||
navn = "Tak"
|
||||
type = "tak"
|
||||
areal = 600.0
|
||||
u_verdi = 0.13
|
||||
|
||||
[[flate]]
|
||||
navn = "Gulv"
|
||||
type = "gulv"
|
||||
areal = 600.0
|
||||
u_verdi = 0.10
|
||||
|
||||
[[vindu]]
|
||||
navn = "Sør"
|
||||
areal = 150.0
|
||||
orientering = 180
|
||||
u_verdi = 0.8
|
||||
g_verdi = 0.5
|
||||
|
||||
[infiltrasjon]
|
||||
n50 = 0.6
|
||||
|
||||
[ventilasjon]
|
||||
type = "balansert"
|
||||
gjenvinning = 0.85
|
||||
kjolebatteri = {kjolebatteri}
|
||||
|
||||
[[oppvarming.kilde]]
|
||||
type = "direkte_el"
|
||||
andel_rom = 1.0
|
||||
andel_tappevann = 1.0
|
||||
"#
|
||||
);
|
||||
toml::from_str(&s).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, hva: &str) {
|
||||
assert!(
|
||||
(faktisk - forventet).abs() <= 0.1,
|
||||
"{hva}: beregnet {faktisk:.2}, forventet {forventet:.2}"
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn driftsdager_per_aar() {
|
||||
let kilde = Datakilde::default();
|
||||
for (kategori, dager) in [
|
||||
(Kategori::Smaahus, 365),
|
||||
(Kategori::Boligblokk, 365),
|
||||
(Kategori::Barnehage, 261),
|
||||
(Kategori::Kontorbygg, 261),
|
||||
(Kategori::Kulturbygg, 261),
|
||||
(Kategori::Skolebygg, 220),
|
||||
(Kategori::Idrettsbygg, 220),
|
||||
] {
|
||||
let n = kilde.normerte(kategori).unwrap();
|
||||
assert_eq!(
|
||||
n.driftstid.driftsdager_per_aar(),
|
||||
dager,
|
||||
"{}",
|
||||
kategori.nokkel()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/// Fellesferien og helgene er uten drift i skolebygg.
|
||||
#[test]
|
||||
fn skolebygg_stengt_i_helg_og_ferie() {
|
||||
let n = Datakilde::default().normerte(Kategori::Skolebygg).unwrap();
|
||||
let d = &n.driftstid;
|
||||
assert!(d.driftsdag(0), "1. januar er mandag i uke 1");
|
||||
assert!(!d.driftsdag(5), "lørdag");
|
||||
assert!(!d.driftsdag(6), "søndag");
|
||||
assert!(!d.driftsdag(7 * 28), "mandag i uke 29");
|
||||
assert!(d.driftsdag(7 * 34), "mandag i uke 35");
|
||||
}
|
||||
|
||||
/// Belysning, utstyr og varmtvann skal gi energibehovene som følger av tabellverdiene.
|
||||
#[test]
|
||||
fn faste_poster_som_tabellverdiene() {
|
||||
let kilde = Datakilde::default();
|
||||
for (kategori, belysning, utstyr, varmtvann) in [
|
||||
("barnehage", 20.9, 5.2, 10.0),
|
||||
("kontorbygg", 25.1, 34.5, 5.0),
|
||||
("skolebygg", 22.0, 13.2, 10.0),
|
||||
("idrettsbygg", 21.1, 2.6, 50.2),
|
||||
("kulturbygg", 23.0, 2.9, 10.0),
|
||||
] {
|
||||
let r = kjor::kjor(&prøvebygg(kategori, false), &kilde).unwrap();
|
||||
naer(post(&r, "5"), belysning, &format!("{kategori} belysning"));
|
||||
naer(post(&r, "6"), utstyr, &format!("{kategori} utstyr"));
|
||||
naer(post(&r, "2"), varmtvann, &format!("{kategori} varmtvann"));
|
||||
}
|
||||
}
|
||||
|
||||
/// Kjølebatteriet gir ventilasjonskjøling; uten det er posten null.
|
||||
#[test]
|
||||
fn kjolebatteri_gir_ventilasjonskjoling() {
|
||||
let kilde = Datakilde::default();
|
||||
let uten = kjor::kjor(&prøvebygg("kontorbygg", false), &kilde).unwrap();
|
||||
let med = kjor::kjor(&prøvebygg("kontorbygg", true), &kilde).unwrap();
|
||||
assert_eq!(post(&uten, "3b"), 0.0);
|
||||
assert!(
|
||||
post(&med, "3b") > 0.5,
|
||||
"ventilasjonskjøling {:.2}",
|
||||
post(&med, "3b")
|
||||
);
|
||||
// Kjøling skjer bare i driftstiden på driftsdager.
|
||||
let ts = &med.timeserie;
|
||||
let lørdag_middag = 5 * 24 + 12 + 24 * 7 * 26;
|
||||
assert_eq!(ts.ventilasjonskjoling[lørdag_middag], 0.0);
|
||||
}
|
||||
@@ -86,13 +86,13 @@ fn regresjonsvakt_for_romoppvarming() {
|
||||
let r = kjor_referansebygg();
|
||||
naer(
|
||||
post(&r, "1a"),
|
||||
27.2,
|
||||
27.1,
|
||||
1.5,
|
||||
"romoppvarming (regresjon, publisert verdi 46,2)",
|
||||
);
|
||||
naer(
|
||||
r.budsjett.netto_spesifikk(r.lost.bra),
|
||||
86.7,
|
||||
86.6,
|
||||
2.0,
|
||||
"netto energibehov (regresjon, publisert verdi 106,4)",
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user