R-Skript Tutorial: Daten nachvollziehbar aufbereiten
Die Daten, die du als OGD veröffentlichen möchtest, liegen jährlich (oder in anderen regelmässigen Abständen) vor? Du möchtest selbst nachvollziehen, wie du die Daten das letzte Jahr aufbereitet hast oder deine Datenaufbereitung in Zukunft einfach übergeben können?
Hier findest du für diesen Fall einige Beispiele, wie du aus einer relativ unstrukturierten Excel-Tabelle in nachvollziehbarer Art und Weise OGD erstellen kannst. Das beste daran? Du kannst die Daten auch direkt per Code in den Datenkatalog laden, ohne den Umweg über die grafische Oberfläche zu nehmen.
Als Tool verwenden wir die Skriptsprache R. Diese ist im Kanton Zürich weit verbreitet und ganz einfach über das Software-Center zu beziehen. Eine Anleitung findest du hier: Datenanalyse mit R / R-Studio (Link funktioniert nur innerhalb des Kantons).
Du bist nach diesen Beispielen auf den Geschmack gekommen und möchtest herausfinden was mit R sonst noch so möglich ist? Hier geht's direkt zum R-Kurs für kantonale Angestellte: rstatsZH
Ein Beispiel mit kantonalen Fahrzeugdaten
Als Beispiel dienen uns echte Daten zu Neubeschaffungen bei der kantonalen Fahrzeugflotte. Diese werden vom Amt für Abfall, Wasser, Energie und Luft (AWEL) des Kantons Zürich erhoben und hier als OGD publiziert: Datenkatalog | Kanton Zürich. Die Erhebung der Daten startet aber (wie so oft) in Excel...
| Treibstoffarten: | |||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Benzin | Diesel | Gas | Hybrid | Plugin-Hybrid | Batterie-Elektrisch | Brennstoff-Zelle | Gesamt | CO2-frei | Plugin Hybrid | Rest | fossil | ||||||
| Personenwagen (M1) | 2020 | Personenwagen (M1) | 2020 | 3 | 53 | 0 | 8 | 27 | 3 | 2 | 96 | 5% | 28% | 67% | 95% | ||
| Personenwagen (M1) | 2021 | 3 | 37 | 0 | 3 | 9 | 17 | 0 | 69 | 25% | 13% | 62% | 75% | ||||
| 2022 | Personenwagen (M1) | 2022 | 2 | 40 | 0 | 0 | 6 | 18 | 0 | 66 | 27% | 9% | 64% | 73% | |||
| Personenwagen (M1) | 2023 | 2 | 42 | 0 | 0 | 0 | 39 | 0 | 83 | 47% | 0% | 53% | 53% | ||||
| 2024 | Personenwagen (M1) | 2024 | 4 | 37 | 0 | 1 | 1 | 63 | 0 | 106 | 59% | 1% | 40% | 40% | |||
| Lieferwagen (N1) | 2020 | Lieferwagen (N1) | 2020 | 0 | 20 | 0 | 0 | 0 | 0 | 0 | 20 | 0% | 0% | 100% | 100% | ||
| Lieferwagen (N1) | 2021 | 0 | 2 | 0 | 0 | 0 | 5 | 0 | 7 | 71% | 0% | 29% | 29% | ||||
| 2022 | Lieferwagen (N1) | 2022 | 0 | 6 | 0 | 0 | 0 | 5 | 0 | 11 | 45% | 0% | 55% | 55% | |||
| Lieferwagen (N1) | 2023 | 0 | 13 | 0 | 0 | 0 | 6 | 0 | 19 | 32% | 0% | 68% | 68% | ||||
| 2024 | Lieferwagen (N1) | 2024 | 1 | 6 | 0 | 0 | 0 | 2 | 0 | 9 | 22% | 0% | 78% | 78% | |||
| Schwere Nutzfahrzeuge (N2, N3) | 2020 | Schwere Nutzfahrzeuge (N2,N3) | 2020 | 0 | 5 | 0 | 0 | 0 | 0 | 0 | 5 | 0% | 0% | 100% | 100% | ||
| Schwere Nutzfahrzeuge (N2,N3) | 2021 | 0 | 10 | 0 | 0 | 0 | 0 | 0 | 10 | 0% | 0% | 100% | 100% | ||||
| 2022 | Schwere Nutzfahrzeuge (N2,N3) | 2022 | 0 | 9 | 0 | 0 | 0 | 0 | 0 | 9 | 0% | 0% | 100% | 100% | |||
| Schwere Nutzfahrzeuge (N2,N3) | 2023 | 0 | 5 | 0 | 0 | 0 | 0 | 0 | 5 | 0% | 0% | 100% | 100% | ||||
| 2024 | Schwere Nutzfahrzeuge (N2,N3) | 2024 | 0 | 7 | 0 | 0 | 0 | 0 | 0 | 7 | 0% | 0% | 100% | 100% | |||
| Alle Fahrzeuge | 2020 | 3 | 78 | 0 | 8 | 27 | 3 | 2 | 121 | 4% | 22% | 74% | 96% | ||||
| Alle Fahrzeuge | 2021 | 3 | 49 | 0 | 3 | 9 | 22 | 0 | 86 | 26% | 10% | 64% | 74% | ||||
| Alle Fahrzeuge | 2022 | 2 | 55 | 0 | 0 | 6 | 23 | 0 | 86 | 27% | 7% | 66% | 73% | ||||
| Alle Fahrzeuge | 2023 | 2 | 60 | 0 | 0 | 0 | 45 | 0 | 107 | 42% | 0% | 58% | 58% | ||||
| Alle Fahrzeuge | 2024 | 5 | 50 | 0 | 1 | 1 | 65 | 0 | 122 | 53% | 1% | 46% | 47% | ||||
| fahrzeugtyp_bezeichnung | jahr | treibstoff_bezeichnung | anzahl |
|---|---|---|---|
| Lieferwagen (N1) | 2020 | Batterieelektrisch | 0 |
| Lieferwagen (N1) | 2020 | Benzin | 0 |
| Lieferwagen (N1) | 2020 | Brennstoffzelle | 0 |
| Lieferwagen (N1) | 2020 | Diesel | 20 |
| Lieferwagen (N1) | 2020 | Gas | 0 |
| Lieferwagen (N1) | 2020 | Hybrid | 0 |
| Lieferwagen (N1) | 2020 | Plug-in Hybrid | 0 |
| Lieferwagen (N1) | 2021 | Batterieelektrisch | 5 |
| Lieferwagen (N1) | 2021 | Benzin | 0 |
| Lieferwagen (N1) | 2021 | Brennstoffzelle | 0 |
| Lieferwagen (N1) | 2021 | Diesel | 2 |
| Lieferwagen (N1) | 2021 | Gas | 0 |
| Lieferwagen (N1) | 2021 | Hybrid | 0 |
| Lieferwagen (N1) | 2021 | Plug-in Hybrid | 0 |
| Lieferwagen (N1) | 2022 | Batterieelektrisch | 5 |
| Lieferwagen (N1) | 2022 | Benzin | 0 |
| Lieferwagen (N1) | 2022 | Brennstoffzelle | 0 |
| Lieferwagen (N1) | 2022 | Diesel | 6 |
| Lieferwagen (N1) | 2022 | Gas | 0 |
| Lieferwagen (N1) | 2022 | Hybrid | 0 |
| Lieferwagen (N1) | 2022 | Plug-in Hybrid | 0 |
| Lieferwagen (N1) | 2023 | Batterieelektrisch | 6 |
| Lieferwagen (N1) | 2023 | Benzin | 0 |
| Lieferwagen (N1) | 2023 | Brennstoffzelle | 0 |
| Lieferwagen (N1) | 2023 | Diesel | 13 |
| Lieferwagen (N1) | 2023 | Gas | 0 |
| Lieferwagen (N1) | 2023 | Hybrid | 0 |
| Lieferwagen (N1) | 2023 | Plug-in Hybrid | 0 |
| Lieferwagen (N1) | 2024 | Batterieelektrisch | 2 |
| Lieferwagen (N1) | 2024 | Benzin | 1 |
| Lieferwagen (N1) | 2024 | Brennstoffzelle | 0 |
| Lieferwagen (N1) | 2024 | Diesel | 6 |
| Lieferwagen (N1) | 2024 | Gas | 0 |
| Lieferwagen (N1) | 2024 | Hybrid | 0 |
| Lieferwagen (N1) | 2024 | Plug-in Hybrid | 0 |
| Personenwagen (M1) | 2020 | Batterieelektrisch | 3 |
| Personenwagen (M1) | 2020 | Benzin | 3 |
| Personenwagen (M1) | 2020 | Brennstoffzelle | 2 |
| Personenwagen (M1) | 2020 | Diesel | 53 |
| Personenwagen (M1) | 2020 | Gas | 0 |
| Personenwagen (M1) | 2020 | Hybrid | 8 |
| Personenwagen (M1) | 2020 | Plug-in Hybrid | 27 |
| Personenwagen (M1) | 2021 | Batterieelektrisch | 17 |
| Personenwagen (M1) | 2021 | Benzin | 3 |
| Personenwagen (M1) | 2021 | Brennstoffzelle | 0 |
| Personenwagen (M1) | 2021 | Diesel | 37 |
| Personenwagen (M1) | 2021 | Gas | 0 |
| Personenwagen (M1) | 2021 | Hybrid | 3 |
| Personenwagen (M1) | 2021 | Plug-in Hybrid | 9 |
| Personenwagen (M1) | 2022 | Batterieelektrisch | 18 |
| Personenwagen (M1) | 2022 | Benzin | 2 |
| Personenwagen (M1) | 2022 | Brennstoffzelle | 0 |
| Personenwagen (M1) | 2022 | Diesel | 40 |
| Personenwagen (M1) | 2022 | Gas | 0 |
| Personenwagen (M1) | 2022 | Hybrid | 0 |
| Personenwagen (M1) | 2022 | Plug-in Hybrid | 6 |
| Personenwagen (M1) | 2023 | Batterieelektrisch | 39 |
| Personenwagen (M1) | 2023 | Benzin | 2 |
| Personenwagen (M1) | 2023 | Brennstoffzelle | 0 |
| Personenwagen (M1) | 2023 | Diesel | 42 |
| Personenwagen (M1) | 2023 | Gas | 0 |
| Personenwagen (M1) | 2023 | Hybrid | 0 |
| Personenwagen (M1) | 2023 | Plug-in Hybrid | 0 |
| Personenwagen (M1) | 2024 | Batterieelektrisch | 63 |
| Personenwagen (M1) | 2024 | Benzin | 4 |
| Personenwagen (M1) | 2024 | Brennstoffzelle | 0 |
| Personenwagen (M1) | 2024 | Diesel | 37 |
| Personenwagen (M1) | 2024 | Gas | 0 |
| Personenwagen (M1) | 2024 | Hybrid | 1 |
| Personenwagen (M1) | 2024 | Plug-in Hybrid | 1 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Batterieelektrisch | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Benzin | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Brennstoffzelle | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Diesel | 5 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Gas | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2020 | Plug-in Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Batterieelektrisch | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Benzin | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Brennstoffzelle | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Diesel | 10 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Gas | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2021 | Plug-in Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Batterieelektrisch | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Benzin | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Brennstoffzelle | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Diesel | 9 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Gas | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2022 | Plug-in Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Batterieelektrisch | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Benzin | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Brennstoffzelle | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Diesel | 5 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Gas | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2023 | Plug-in Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Batterieelektrisch | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Benzin | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Brennstoffzelle | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Diesel | 7 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Gas | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Hybrid | 0 |
| Schwere Nutzfahrzeuge (N2/N3) | 2024 | Plug-in Hybrid | 0 |
R-Tutorial: Von Excel zur OGD-konformen CSV-Datei
Folgendes R-Script zeigt Schritt für Schritt, wie die Excel-Datei in eine OGD-konforme CSV umgewandelt wird. Es dient als Inspiration und Vorlage für ähnliche Datensätze.
# ============================================================
# Tutorial: Von Excel zu Open Government Data (CSV)
# ============================================================
# Ziel dieses Skripts:
# - Du liest eine Excel-Datei roh ein
# - Du entfernst leere Zeilen und Spalten
# - Du wählst die relevanten Spalten aus
# - Du vergibst klare Spaltennamen
# - Du formst die Tabelle von "breit" nach "lang" um
# - Du exportierst eine saubere CSV-Datei für OGD
#
# Benötigte Pakete:
# install.packages(c("readxl", "dplyr", "tidyr", "readr", "janitor"))
# ============================================================
# -----------------------------
# 1) Dateipfade festlegen
# -----------------------------
# Lege hier fest, wie deine Eingabe- und Ausgabedatei heissen.
# Am einfachsten ist es, wenn Excel-Datei und Quarto-Datei im gleichen Projekt liegen.
pfad_excel <- "data/AWEL_Beispiel.xlsx"
pfad_csv <- "data/Fahrzeugflotte_OGD.csv"
# -----------------------------
# 2) Excel-Datei roh einlesen
# -----------------------------
# Die Excel-Datei enthält am Anfang noch Titelzeilen und Leerzeilen.
# Darum lesen wir zuerst alles ohne feste Spaltennamen ein.
excel_roh <- readxl::read_excel(
path = pfad_excel,
sheet = 1,
col_names = FALSE
)
# Optional: Rohdaten kurz ansehen
print(utils::head(excel_roh, 10))
# -----------------------------
# 3) Leere Zeilen und Spalten entfernen
# -----------------------------
# Excel-Dateien enthalten oft leere Zeilen oder leere Spalten am Rand.
# Diese brauchen wir für die weitere Verarbeitung nicht.
excel_roh <- excel_roh |>
janitor::remove_empty("rows") |>
janitor::remove_empty("cols")
# Optional: Bereinigte Rohdaten ansehen
print(utils::head(excel_roh, 10))
# -----------------------------
# 4) Relevante Spalten auswählen
# -----------------------------
# In dieser Beispieldatei stehen die relevanten Daten in den Spalten 3 bis 11:
# - Fahrzeugart
# - Jahr
# - 7 Spalten mit Antriebstechnologien
excel_relevant <- excel_roh |>
dplyr::select(3:11)
# -----------------------------
# 5) Klare Spaltennamen setzen
# -----------------------------
# Die Excel-Datei bringt hier keine direkt brauchbaren Spaltennamen mit.
# Darum vergeben wir die Namen bewusst von Hand.
names(excel_relevant) <- c(
"fahrzeugart",
"jahr",
"benzin",
"diesel",
"gas",
"hybrid",
"plug_in_hybrid",
"batterieelektrisch",
"brennstoffzelle"
)
# Optional: Spaltennamen prüfen
names(excel_relevant)
# -----------------------------
# 6) Nur echte Datenzeilen behalten
# -----------------------------
# Die ersten Zeilen enthalten noch Überschriften oder Titel.
# Echte Datenzeilen erkennst du hier daran, dass ein Jahr vorhanden ist.
excel_daten <- excel_relevant |>
dplyr::filter(!is.na(jahr))
# -----------------------------
# 7) Summenzeilen entfernen
# -----------------------------
# In der Excel-Datei gibt es zusätzlich die Zeile "Alle Fahrzeuge".
# Diese wird in der publizierten OGD-Datei nicht verwendet. Dient höchstens der Kontrolle der abgeschlossenen Aufbereitung.
excel_daten <- excel_daten |>
dplyr::filter(fahrzeugart != "Alle Fahrzeuge")
# -----------------------------
# 8) Fahrzeugtyp vereinheitlichen
# -----------------------------
# Kleinere Unterschiede in der Schreibweise werden vereinheitlicht.
excel_daten <- excel_daten |>
dplyr::mutate(
fahrzeugart = dplyr::case_when(
fahrzeugart == "Schwere Nutzfahrzeuge (N2,N3)" ~ "Schwere Nutzfahrzeuge (N2/N3)",
TRUE ~ fahrzeugart
)
)
# -----------------------------
# 9) Von breit nach lang umformen
# -----------------------------
# Aus mehreren Spalten zu Antriebstechnologien wird:
# - eine Spalte mit der Technologie
# - eine Spalte mit dem Wert
ogd_daten <- excel_daten |>
tidyr::pivot_longer(
cols = c(
benzin,
diesel,
gas,
hybrid,
plug_in_hybrid,
batterieelektrisch,
brennstoffzelle
),
names_to = "antriebstechnologie",
values_to = "anzahl_fzg"
)
# -----------------------------
# 10) Namen der Antriebstechnologien lesbarer machen
# -----------------------------
# Die technischen Spaltennamen werden wieder in gut lesbare Werte umgewandelt.
ogd_daten <- ogd_daten |>
dplyr::mutate(
antriebstechnologie = dplyr::case_when(
antriebstechnologie == "benzin" ~ "Benzin",
antriebstechnologie == "diesel" ~ "Diesel",
antriebstechnologie == "gas" ~ "Gas",
antriebstechnologie == "hybrid" ~ "Hybrid",
antriebstechnologie == "plug_in_hybrid" ~ "Plug-in Hybrid",
antriebstechnologie == "batterieelektrisch" ~ "Batterieelektrisch",
antriebstechnologie == "brennstoffzelle" ~ "Brennstoffzelle",
TRUE ~ antriebstechnologie
)
)
# -----------------------------
# 11) Datentypen bereinigen
# -----------------------------
# Für OGD sollen Zahlen auch wirklich als Zahlen vorliegen. Dies ist auch eine Vorsichtsmassnahme.
ogd_daten <- ogd_daten |>
dplyr::mutate(
jahr = as.integer(jahr),
anzahl_fzg = as.integer(anzahl_fzg)
)
# -----------------------------
# 12) Lesbare Spaltennamen setzen
# -----------------------------
# Für die veröffentlichte Datei verwenden wir gut verständliche Namen.
ogd_daten <- ogd_daten |>
dplyr::rename(
Fahrzeugtyp = fahrzeugart,
Jahr = jahr,
Antriebstechnologie = antriebstechnologie,
Anzahl_Fzg = anzahl_fzg
)
# -----------------------------
# 13) Fehlende Werte prüfen
# -----------------------------
# Diese Prüfung hilft dir zu sehen, ob in der fertigen Tabelle
# noch wichtige Werte fehlen.
summe_na <- ogd_daten |>
dplyr::summarise(
fehlende_fahrzeugtypen = sum(is.na(Fahrzeugtyp)),
fehlende_jahre = sum(is.na(Jahr)),
fehlende_antriebe = sum(is.na(Antriebstechnologie)),
fehlende_anzahl = sum(is.na(Anzahl_Fzg))
)
print(summe_na)
cat("Anzahl Zeilen in der OGD-Tabelle:", nrow(ogd_daten), "\n")
# -----------------------------
# 14) Optional: Dubletten prüfen
# -----------------------------
# Dieser Schritt ist optional.
# Er zeigt dir, ob Kombinationen aus Fahrzeugtyp, Jahr und
# Antriebstechnologie mehrfach vorkommen.
duplikate <- ogd_daten |>
janitor::get_dupes(Fahrzeugtyp, Jahr, Antriebstechnologie)
print(duplikate)
# -----------------------------
# 15) Sortieren
# -----------------------------
# Eine saubere Sortierung macht die Datei lesbarer.
ogd_daten <- ogd_daten |>
dplyr::arrange(Fahrzeugtyp, Jahr, Antriebstechnologie)
# -----------------------------
# 16) CSV exportieren
# -----------------------------
# Die Datei wird als UTF-8-CSV geschrieben. MIT BOM um sie einfach in Excel zu öffnen.
readr::write_excel_csv2(
x = ogd_daten,
file = pfad_csv,
na = ""
)
cat("Fertig. Die CSV-Datei wurde erstellt:", pfad_csv, "\n")
# -----------------------------
# 17) Ergebnis ansehen
# -----------------------------
print(utils::head(ogd_daten, 20))
R-Tutorial: Automatisierter Upload in den Datenkatalog
Die oben erstellte CSV-Datei wäre nun bereit um als OGD-Ressource in die Metadatenverwaltung hochgeladen zu werden. Wozu aber noch mühsam händisch die Datei hochladen, wenn wir doch auch alles in einem Rutsch per R-Skript machen könnten?
Mit nur wenigen Zeilen Code haben wir auch den Upload erledigt. Das Code-Beispiel folgt dabei grösstenteils dem readme des von uns zur Verfügung gestellten zhapir.
# -----------------------------
# 18) Optional: Distribution in der MDV aktualisieren
# -----------------------------
# Dieser Schritt ist optional.
# Wenn du die fertige CSV-Datei direkt in der MDV nachführen willst,
# kannst du dafür das Paket zhapir verwenden.
#
# WICHTIG:
# - Du brauchst dafür einen gültigen API Key. Wie du diesen bekommst, steht im readme des Packages auf Github.
# - Der API Key muss als ZHAPIR_API_KEY in deiner .Renviron-Datei stehen.
# - Für produktive Änderungen immer use_dev = FALSE setzen.
#
# Installation bei Bedarf:
# remotes::install_github("openZH/zhapir")
#
# Trage hier die ID deiner bestehenden Distribution ein.
# Diese ID findest du in der grafischen Oberfläche des MDV.
distribution_id <- 12345
# Optional: nächstes geplantes Aktualisierungsdatum
naechstes_update <- "2026-01-01"
# Optional: Enddatum des aktuell beschriebenen Datenstands
enddatum <- "2025-12-31"
# Distribution aktualisieren und neue Datei hochladen
verteilung_update <- zhapir::update_distribution(
id = distribution_id,
file_path = pfad_csv,
modified_next = naechstes_update,
end_date = enddatum,
use_dev = FALSE
)
print(verteilung_update)
cat("Die Distribution in der MDV wurde aktualisiert.\n")
Erklärung der wichtigsten Schritte
-
Warum lesen wir die Excel-Datei zuerst roh ein?
Viele Excel-Dateien sind nicht so aufgebaut, dass die erste Zeile sofort als sauberer Tabellenkopf verwendet werden kann. In deinem Beispiel gibt es zuerst Überschriften, Strukturzeilen und leere Bereiche. Darum ist es einfacher, zuerst alles einzulesen und danach gezielt die relevanten Teile herauszunehmen. -
Warum verwenden wir
janitor::remove_empty()?
Excel-Dateien enthalten oft leere Zeilen oder leere Spalten, die nur für das Layout da sind.janitor::remove_empty()entfernt diese Elemente früh im Prozess und macht die Tabelle einfacher weiterzuverarbeiten. -
Warum setzen wir die Spaltennamen hier von Hand?
In dieser Beispieldatei stehen die Daten zwar an einer gut erkennbaren Stelle, aber nicht in einer perfekt vorbereiteten Tabelle mit sofort nutzbaren Spaltennamen. Für ein Einsteiger-Tutorial ist es deshalb einfacher, zuerst die relevanten Spalten auszuwählen und ihnen dann bewusst klare Namen zu geben. -
Warum formen wir von breit nach lang um?
Breite Tabellen sind für Menschen oft gut lesbar. Für OGD und Datenverarbeitung ist eine lange Tabelle aber meistens besser. Anstatt separater Spalten für Benzin, Diesel und Gas enthält diese eine Spalte für den Technologienamen und eine weitere für den zugehörigen Wert. Das ist sauberer, standardisierter und einfacher auszuwerten.
Typische Fehler und wie du damit umgehst
-
Fehler 1: Datei wird nicht gefunden
Beispiel:Error: path does not exist. Dann stimmt meistens der Dateipfad nicht. Prüfe:- Liegt die Excel-Datei im richtigen Ordner?
- Ist der Dateiname exakt richtig geschrieben?
- Stimmt die Dateiendung
.xlsx?
-
Fehler 2: Ein Paket fehlt
Beispiel:there is no package called ...
Dann installiere das fehlende Paket mitinstall.packages(...). -
Fehler 3: Die ausgewählten Spalten passen nicht
Das Tutorial basiert auf einer konkreten Excel-Struktur. Wenn sich die Quelldatei im nächsten Jahr verändert, kann es sein, dass die relevanten Daten nicht mehr in den Spalten 3 bis 11 stehen.
Prüfe dann zuerst die Rohdaten mit:print(utils::head(excel_roh, 10))und passe danach die Spaltenauswahl indplyr::select()an. -
Fehler 4: Eine Spalte wird nicht gefunden
Beispiel:Can't select columns that don't exist
Dann stimmen die Spaltennamen im Skript nicht mehr zur Excel-Datei. Prüfe mit:names(excel_relevant). Passe danach die Namen oder die Auswahl im Skript an. -
Fehler 5: zhapir kann nicht auf die MDV zugreifen. Fehler 401, 404 oder 500.
Prüfe in diesem Fall:- Ist das Paket
zhapirinstalliert? - Ist dein API Key als
ZHAPIR_API_KEYin der.Renvirongespeichert? - Hast du die R-Session nach dem Eintrag in
.Renvironneu gestartet? - Verwendest du die richtige ID für Datensatz oder Distribution?
- Ist
use_dev = FALSEgesetzt, wenn du produktiv arbeiten willst?
- Ist das Paket
Was du ein LLM fragen kannst
Gerade am Anfang kann ein LLM sehr hilfreich sein. Gute Fragen sind zum Beispiel:
- „Erkläre mir diesen R-Code Zeile für Zeile.“
- „Warum brauche ich
pivot_longer()in diesem Skript?“ - „Wie passe ich das Skript an, wenn meine Excel-Datei andere Spalten hat?“
- „Wie prüfe ich in R, ob meine OGD-Datei fehlende Werte enthält?“
- „Hilf mir, diese Fehlermeldung in R zu verstehen.“
Wichtig ist: Kopiere bei Problemen immer die vollständige Fehlermeldung mit.
Kopiere keine internen oder vertraulichen Daten in das Chatfenster mit dem LLM.
Hinweis zum Beispiel
Dieses Tutorial basiert auf einer konkreten Excel-Struktur. Prüfe bei neuen Jahresdateien immer kurz,
- ob die relevanten Daten noch in denselben Spalten stehen,
- ob die Spaltennamen noch passen,
- und ob die fertige OGD-Tabelle plausibel ist.