Preliminaries —–

Thema und Daten —–

Die Daten stammen von . Diese Datenbank umfasst Millionen publizierte Medienartikel aus einer Vielzahl von Schweizer Medienquellen (print und digital). Für meine Analyse wurden alle Deutschsprachige Artikel der letzten 20 Jahren heruntergeladen.

Der heruntergeladene Datensatz war zu gross um ihn in R direkt einlesen zu können. Aus diesem Grund wurde dieser in Python anhand der Dictionnaries gefilitert.

Thema und Forschungsfrage —–

Der Fokus meiner Untersuchungen liegt auf die Genderanalyse im Sportbereich. Bei vielen Sportarten gibt es sehr starke Genderimbalance (mehr Frauen praktizieren Eiskunstlauf, Männerfussball ist viel populärer, Einkommensunterschiede usw.). Deshalb habe ich mich entschieden, meine Analyse auf den alpinen Skisport zu fokussiern, denn dieser Sport geniesst nicht nur in der Schweiz grosse Popularität, sondern es gibt auch kein signifikantes Ungleichgewicht zwischen den Geschlechtern in dieser Sportart.

Dementsprechend widmet sich meine deskriptive Analyse der folgenden Forschungsfrage: Wie werden Skifahrerinnen im Vergleich zu Skifahrer in den Schweizer Medien dargestellt?

Bilden der Dictionnaries —–

Um meinen Korpus zu bilden habe ich einen Dictionnary mit Vornamen und Namen der Skimeister (Kategorien: Abfahrt, Super-G, Riesenslalom, Slalom und (Super-)Kombination), der letzten 20 Jahren, erstellt. Einen Dictionnary für die Frauen und einen für die Männer.

Tabelle der MeisterInnen: https://de.wikipedia.org/wiki/Liste_der_Schweizer_Meister_im_alpinen_Skisport

Python Code für Skimeisterinnen:

import pandas as pd

# Define chunk size and substring list
chunk_size = 10000
substring_list = ["tamara müller", "tamara mueller", "sonja nef", "marlies oester", "marlies öster", "nadia styger", "tanja pieren", "fabienne suter",
                   "erika dicht", "fränzi aufdenblatten", "fraenzi aufdenblatten", "franziska christine aufdenblatten", "franziska aufdenblatten", "lilian kummer",
                     "eliane volken", "miriam gmür", "miriam gmuer", "marianne abderhalden", "tina weirather", "christina weirather", "aita camastral", 
                     "andrea dettling", "sylviane berthod", "lara gut", "lara gut-behrami", "pascale berthod", "aline bonjour", "martina schild", "rabea grand", 
                     "jessica pünchera", "jessica puenchera", "nadja jnglin-kamer", "nadja kamer", "marina nigg", "jasmine flury", "esther good", "margaux givel", 
                     "wendy holdener", "corinne suter", "dominique gisin", "dominique sabine gisin", "jasmina suter", "denise feierabend", "fabienne suter", "aline danioth",
                       "rahel kopp", "mélanie meillard", "melanie meillard", "priska nufer", "nathalie gröbli", "nathalie groebli", "vivianne härri", "vivianne haerri", "camille rast", 
                       "luana flütsch", "luana fluetsch", "amélie klopfenstein", "amelie klopfenstein", "delia durrer", "noémie kolly", "noemie kolly", "delphine darbellay", "anuk brändli", 
                       "anuk braendli"
                    ]

# Create an empty list to store the filtered dataframes
filtered_dfs = []

# Loop over each chunk of the dataset
for df_chunk in pd.read_csv('Media2000_2023.tsv', sep="\t", encoding='utf-8', chunksize=chunk_size):
    # Check if the 'content' column exists in the chunk
    if 'content' in df_chunk.columns:
        df_chunk['content'] = df_chunk['content'].str.lower()
        # Check if all substrings are strings
        if all(isinstance(sub, str) for sub in substring_list):
            # Join the substrings with the '|' character
            substrings = '|'.join(substring_list)
            # Filter the chunk based on the 'content' column
            filtered_df = df_chunk[df_chunk['content'].str.contains(substrings)]
            # Add the filtered dataframe to the list
            filtered_dfs.append(filtered_df)

# Concatenate all filtered dataframes into one final dataframe
final_df = pd.concat(filtered_dfs)

final_df.to_csv('ski_frauen.csv', index=False)

Python Code für Skimeister:

import pandas as pd

# Define chunk size and substring list
chunk_size = 10000
substring_list = ["didier cuche", "urs imboden", "didier défago", "didier defago", "daniel albrecht", "konrad hari",
                   "bruno kernen", "tobias grünenfelder", "tobias gruenenfelder", "marc berthod", "marc gini", "stéphane de siebenthal",
                     "stephane de siebenthal", "dimitri cuche", "silvan zurbriggen", "patrick küng", "patrick kueng", "justin murisier", "ami oreiller",
                       "markus vogel", "christian spescha", "mauro caviezel", "reto schmidiger", "beat feuz", "vitus lüönd", "vitus lueoend", "thomas tumler", "luca aerni",
                         "luca ärni", "sandro viletta", "urs kryenbühl", "urs kryenbuehl", "bernhard niederberger", "fernando schmed", "loïc meillard", 
                         "loic meillard", "gino caviezel", "marco odermatt", "ramon zenhäusern", "ramon zenhaeusern", "sandro simonet", "gilles roulin", 
                         "cédric noger", "cedric noger", "josua mettler", "marco reymond", "noel von grünigen", "noel von gruenigen", "reto mächler", "reto maechler",
                           "ralph weber", "lars rösti", "lars roesti", "denis corthay", "lenz hächler", "lenz haechler"]

# Create an empty list to store the filtered dataframes
filtered_dfs = []

# Loop over each chunk of the dataset
for df_chunk in pd.read_csv('Media2000_2023.tsv', sep="\t", encoding='utf-8', chunksize=chunk_size):
    # Check if the 'content' column exists in the chunk
    if 'content' in df_chunk.columns:
        df_chunk['content'] = df_chunk['content'].str.lower()
        # Check if all substrings are strings
        if all(isinstance(sub, str) for sub in substring_list):
            # Join the substrings with the '|' character
            substrings = '|'.join(substring_list)
            # Filter the chunk based on the 'content' column
            filtered_df = df_chunk[df_chunk['content'].str.contains(substrings)]
            # Add the filtered dataframe to the list
            filtered_dfs.append(filtered_df)

# Concatenate all filtered dataframes into one final dataframe
final_df = pd.concat(filtered_dfs)

final_df.to_csv('ski_männer.csv', index=False)

Einlesen der Daten —-

ski_frau <- read.csv("C:/Users/arnol/Desktop/UZH_Master/FS23/Forschungsseminar Politischer Datenjournalismus/Blog/blog_R/data/ski_frauen.csv")

ski_mann <- read.csv("C:/Users/arnol/Desktop/UZH_Master/FS23/Forschungsseminar Politischer Datenjournalismus/Blog/blog_R/data/ski_manner.csv")

Data Wrangling —-

Einfügen einer Gender Variable —-

\(\bullet\) Frauen für Frauen
\(\bullet\) Männer für Männer

#frauen
ski_frau <- mutate(ski_frau, Geschlecht = "Frauen")
janitor::tabyl(ski_frau$Geschlecht)
#männer
ski_mann <- mutate(ski_mann, Geschlecht = "Männer") 
janitor::tabyl(ski_mann$Geschlecht)

Datensätze verbinden —-

ski_bind <- rbind(ski_mann, ski_frau)

Bereinigung —-

Jahre
Jahre anstatt Datum und nur ab 2003 (i.e. letzte 20 Jahre)

#datum in jahr
ski <- ski_bind %>%
  mutate(date = as.Date(pubtime))

ski$jahr <- format(as.Date(ski$date, format = "%Y%m%d"), format = "%Y")

tabyl(ski$jahr)

#2003-2023
ski <- ski %>%
  filter(jahr > 2002)
class(ski$jahr) #character

ski$jahr <- as.numeric(ski$jahr)

Html-Code
html-Code entfernen

ski <- ski %>%
  mutate(text = gsub("<.*?>", " ", content))

Mediengrösse
Ich habe mich entschieden die lokalen Zeitungen zu entfernen, da diese einen Bias bezüglich Sportler aus ihrer Region enthalten könnten.

Um nach grösse regionale und überregionale Medien im Datensatz zu filtern habe ich an die im FOEG aufgelisteten Zeitungen orientiert: https://www.foeg.uzh.ch/de/jahrbuch-qualit%C3%A4t-der-medien/hauptbefunde.html

Zusätzlich habe ich den Schweizer Illustrierter auch in den Datensatz miteinbezogen.

#print(unique(ski$medium_name))
table(ski_frau$medium_name)

ski1 <- ski %>%
  filter(medium_name %in% c("Aargauer Zeitung / MLZ", "Basler Zeitung", 
                         "Berner Zeitung", "Der Bund", "Neue Luzerner Zeitung", "Luzerner Zeitung",
                         "Neue Zürcher Zeitung", "St. Galler Tagblatt", "Tages-Anzeiger",
                         "Blick", "20 Minuten", "NZZ am Sonntag", "Schweiz am Sonntag / MLZ",
                         "SonntagsZeitung", "Die Weltwoche", "Die Wochenzeitung",
                         "Sonntagsblick", "nzz.ch", "tagesanzeiger.ch",
                         "luzernerzeitung.ch", "tagblatt.ch", "bazonline.ch",
                         "bernerzeitung.ch", "aargauerzeitung.ch", "blick.ch",
                         "20 minuten", "20 minuten online", "20 Minuten Online",
                         "srf.ch", "Schweizer Illustrierte"))

#write.csv(ski1, file = "ski1.csv") #save file

Überprüfungen uniqueness —–

#every article only once in the dataset
unique_ids <- unique(ski1$id)
length(unique_ids)

#find the duplicated IDs
duplicate_ids <- ski1 %>%
  group_by(id) %>%
  filter(n() > 1) %>%
  distinct(id) %>%
  ungroup()

duplicate_ids ##5393

#remove observations with duplicated IDs from the dataset
ski1_unique <- ski1 %>%
  filter(!(id %in% duplicate_ids$id))
tabyl(ski1$Geschlecht)

#create a separate dataset with duplicated IDs
ski1_duplicates <- ski1 %>%
  filter(id %in% duplicate_ids$id)

tabyl(ski1_duplicates$Geschlecht)

ski1_duplicates ##10934

#group by id and geschlecht, count the occurrences
duplicate_articles <- ski1_duplicates %>%
  group_by(id, Geschlecht) %>%
  summarise(count = n()) %>%
  ungroup()

#filter to keep only the duplicate articles with the same id and geschlecht
duplicate_articles <- duplicate_articles %>%
  filter(count > 1)

Datensatz mit jedem Artikel einmal —–

#Newspaper Filter----
newspapers <- c("Aargauer Zeitung / MLZ", "Basler Zeitung", 
                "Berner Zeitung", "Der Bund", "Neue Luzerner Zeitung", "Luzerner Zeitung",
                "Neue Zürcher Zeitung", "St. Galler Tagblatt", "Tages-Anzeiger",
                "Blick", "20 Minuten", "NZZ am Sonntag", "Schweiz am Sonntag / MLZ",
                "SonntagsZeitung", "Die Weltwoche", "Die Wochenzeitung",
                "Sonntagsblick", "nzz.ch", "tagesanzeiger.ch",
                "luzernerzeitung.ch", "tagblatt.ch", "bazonline.ch",
                "bernerzeitung.ch", "aargauerzeitung.ch", "blick.ch",
                "20 minuten", "20 minuten online", "20 Minuten Online",
                "srf.ch", "Schweizer Illustrierte")

  

#CREATE DF----------------------------------------------------------------------
df_filtered.f <- ski_frau %>%
  filter(medium_name %in% newspapers)

df_filtered.m <- ski_mann %>%
  filter(medium_name %in% newspapers)

##check for duplicate entries
# test <- df_filtered.f[df_filtered.f$content %in% df_filtered.f$content[duplicated(df_filtered.f$content)],]
# test2 <- df_filtered.m[df_filtered.m$content %in% df_filtered.m$content[duplicated(df_filtered.m$content)],]


##merge datasets
df_filtered.f$frau = 1
df_filtered.m$mann = 1

df_combined <- df_filtered.f %>%
  full_join(df_filtered.m, by = names(df_filtered.f)[1:15]) %>%
  mutate(frau = ifelse(is.na(frau), 0, 1)) %>%
  mutate(mann = ifelse(is.na(mann), 0, 1)) %>%
  mutate(jahr = format(as.Date(pubtime), "%Y")) %>%
  filter(jahr > 2002) %>%
  distinct(id, .keep_all = T) %>%
  mutate(text = gsub("<.*?>", " ", content)) %>%
  dplyr::select(-c("Geschlecht.x","Geschlecht.y"))

n_distinct(df_combined$id)

##check for duplicate ids
length(df_combined[df_combined$id %in% df_combined$id[duplicated(df_combined$id)],]$id)

ski2 <- df_combined
#write.csv(ski2, file = "ski2.csv") #save file

Bemerkungen:

\(\bullet\) ski1 enthält alle Artikel in denen Skifahrer oder Skifahrerinnen aus dem Dictionary erwähnt worden sind. D.h. gewisse Artikel mehrmals im Datensatz weil mehrere Männer und Frauen erwähnt.
\(\bullet\) ski2 enthält jeden Artikel (nach id gefiltert) nur einmal. Hier ist Geschlecht anders kodiert. Nähmlich wenn eine Frau erwähnt wurde nimmt frau den Wert 1 ein sonst null. Gleiches bei Männern.