{"spec_id":"line-impurity-comparison","library":"ggplot2","language":"r","code":"#' anyplot.ai\n#' line-impurity-comparison: Gini Impurity vs Entropy Comparison\n#' Library: ggplot2 3.5.1 | R 4.4.1\n#' Quality: 85/100 | Created: 2026-05-29\n\nlibrary(ggplot2)\nlibrary(dplyr)\nlibrary(scales)\nlibrary(ragg)\n\nset.seed(42)\n\n# Theme tokens\nTHEME       <- Sys.getenv(\"ANYPLOT_THEME\", \"light\")\nPAGE_BG     <- if (THEME == \"light\") \"#FAF8F1\" else \"#1A1A17\"\nELEVATED_BG <- if (THEME == \"light\") \"#FFFDF6\" else \"#242420\"\nINK         <- if (THEME == \"light\") \"#1A1A17\" else \"#F0EFE8\"\nINK_SOFT    <- if (THEME == \"light\") \"#4A4A44\" else \"#B8B7B0\"\n\n# Imprint palette — Gini gets brand green (pos 1), Entropy gets lavender (pos 2)\nIMPRINT_PALETTE <- c(\n  \"#009E73\",  # 1 — brand green\n  \"#C475FD\",  # 2 — lavender\n  \"#4467A3\",  # 3 — blue\n  \"#BD8233\",  # 4 — ochre\n  \"#AE3030\",  # 5 — matte red\n  \"#2ABCCD\",  # 6 — cyan\n  \"#954477\",  # 7 — rose\n  \"#99B314\"   # 8 — lime\n)\n\n# Data: probability range [0, 1] with 100 points\np_vals <- seq(0, 1, length.out = 100)\n\ngini_vals <- 2 * p_vals * (1 - p_vals)\n\n# Entropy: 0 at boundaries by convention (lim p->0 p*log2(p) = 0)\nentropy_vals <- ifelse(\n  p_vals == 0 | p_vals == 1,\n  0,\n  -p_vals * log2(p_vals) - (1 - p_vals) * log2(1 - p_vals)\n)\n\ngini_label    <- \"Gini: 2p(1-p)\"\nentropy_label <- \"Entropy: -p log2(p) - (1-p) log2(1-p)\"\n\ndf <- data.frame(\n  p        = rep(p_vals, 2),\n  impurity = c(gini_vals, entropy_vals),\n  metric   = factor(\n    rep(c(gini_label, entropy_label), each = 100),\n    levels = c(gini_label, entropy_label)\n  )\n)\n\n# Plot\nplot_title <- \"line-impurity-comparison · r · ggplot2 · anyplot.ai\"\n\np_plot <- ggplot(df, aes(x = p, y = impurity, color = metric, linetype = metric)) +\n  geom_area(aes(fill = metric), alpha = 0.08, position = \"identity\") +\n  geom_line(linewidth = 1.2) +\n  geom_vline(\n    xintercept = 0.5,\n    color      = INK_SOFT,\n    linewidth  = 0.4,\n    linetype   = \"dotted\"\n  ) +\n  annotate(\n    \"text\",\n    x      = 0.53,\n    y      = 0.88,\n    label  = \"p = 0.5 (max impurity)\",\n    color  = INK_SOFT,\n    size   = 3,\n    hjust  = 0\n  ) +\n  scale_color_manual(\n    name   = \"Splitting Criterion\",\n    values = c(\n      \"Gini: 2p(1-p)\"                                    = IMPRINT_PALETTE[1],\n      \"Entropy: -p log2(p) - (1-p) log2(1-p)\"            = IMPRINT_PALETTE[2]\n    )\n  ) +\n  scale_fill_manual(\n    values = c(\n      \"Gini: 2p(1-p)\"                                    = IMPRINT_PALETTE[1],\n      \"Entropy: -p log2(p) - (1-p) log2(1-p)\"            = IMPRINT_PALETTE[2]\n    ),\n    guide  = \"none\"\n  ) +\n  scale_linetype_manual(\n    name   = \"Splitting Criterion\",\n    values = c(\n      \"Gini: 2p(1-p)\"                                    = \"solid\",\n      \"Entropy: -p log2(p) - (1-p) log2(1-p)\"            = \"dashed\"\n    )\n  ) +\n  scale_x_continuous(\n    breaks = seq(0, 1, 0.25),\n    labels = c(\"0\", \"0.25\", \"0.5\", \"0.75\", \"1\")\n  ) +\n  scale_y_continuous(\n    breaks = seq(0, 1, 0.25),\n    limits = c(0, 1.08)\n  ) +\n  labs(\n    title = plot_title,\n    x     = \"Probability p\",\n    y     = \"Impurity (normalized to [0, 1])\"\n  ) +\n  theme_minimal(base_size = 8) +\n  theme(\n    plot.background   = element_rect(fill = PAGE_BG, color = PAGE_BG),\n    panel.background  = element_rect(fill = PAGE_BG, color = NA),\n    panel.grid.major  = element_line(\n      color     = adjustcolor(INK_SOFT, alpha.f = 0.25),\n      linewidth = 0.3\n    ),\n    panel.grid.minor  = element_blank(),\n    axis.line         = element_line(color = INK_SOFT, linewidth = 0.4),\n    axis.title        = element_text(color = INK,      size = 10),\n    axis.text         = element_text(color = INK_SOFT, size = 8),\n    plot.title        = element_text(color = INK,      size = 12, hjust = 0),\n    legend.background = element_rect(\n      fill      = ELEVATED_BG,\n      color     = adjustcolor(INK_SOFT, alpha.f = 0.4),\n      linewidth = 0.3\n    ),\n    legend.text       = element_text(color = INK_SOFT, size = 8),\n    legend.title      = element_text(color = INK,      size = 10),\n    legend.position   = \"bottom\",\n    legend.key        = element_rect(fill = PAGE_BG, color = NA),\n    plot.margin       = unit(c(0.5, 0.5, 0.3, 0.5), \"cm\")\n  )\n\n# Save\nggsave(\n  filename = sprintf(\"plot-%s.png\", THEME),\n  plot     = p_plot,\n  device   = ragg::agg_png,\n  width    = 8,\n  height   = 4.5,\n  units    = \"in\",\n  dpi      = 400\n)\n"}