1.Carga de Datos y Librerías

library(readxl)
library(dplyr)
library(tidyr)
library(gt)
library(ggplot2)
library(scales)
library(forcats)
datos <- read_excel("dataset_mundial_petro.xlsx")
cat("Número de registros:", nrow(datos), "\n")
## Número de registros: 8334
cat("Número de variables:", ncol(datos), "\n")
## Número de variables: 23

2.Extracción de Variable Aleatoria

La variable Status indica el estado operativo de cada yacimiento. Originalmente tiene 9 categorías puntuales; se excluyen los N/S y se consolidan en 5 condiciones generales, siguiendo la secuencia lógica del ciclo de vida de un yacimiento (de más activo a más inactivo/reconvertido).

n_total <- nrow(datos)
datos_status <- datos %>% filter(Status != "N/S")
n <- nrow(datos_status)

cat("Registros excluidos por N/S:", n_total - n, "\n")
## Registros excluidos por N/S: 266
cat("Número de registros válidos:", n, "\n")
## Número de registros válidos: 8068
datos_status <- datos_status %>%
  mutate(Condición = case_when(
    Status %in% c("operating", "in development") ~ "Activos y en Desarrollo",
    Status %in% c("discovered", "exploration")    ~ "En etapa temprana",
    Status %in% c("shut in", "cancelled")         ~ "Suspendidos o Cancelados",
    Status %in% c("decommissioned", "abandoned")  ~ "Clausura Definitiva",
    Status == "UGS"                               ~ "Reconvertido a Almacenamiento",
    TRUE ~ NA_character_
  ))

# Orden lógico (no por frecuencia) para presentación: de más activo a más inactivo
orden_labels <- c(
  "Activos y en Desarrollo", "En etapa temprana", "Suspendidos o Cancelados",
  "Clausura Definitiva", "Reconvertido a Almacenamiento"
)

datos_status$Condición <- factor(datos_status$Condición,
                                  levels = orden_labels, ordered = TRUE)

conteo <- as.data.frame(table(datos_status$Condición)) %>%
  rename(Estado = Var1, ni = Freq) %>%
  mutate(
    hi     = round(ni / n, 4),
    hi_pct = round(ni / n * 100, 2)
  )

k <- nrow(conteo)
cat("Total de categorías:", k, "\n")
## Total de categorías: 5
cat("Categoría más frecuente:", conteo$Estado[which.max(conteo$ni)],
    "con", max(conteo$ni), "registros\n")
## Categoría más frecuente: 1 con 6584 registros
cat("Categoría menos frecuente:", conteo$Estado[which.min(conteo$ni)],
    "con", min(conteo$ni), "registro(s)\n")
## Categoría menos frecuente: 5 con 11 registro(s)

3.Tabla de Distribución de Frecuencias

fila_total <- tibble(
  Estado  = "TOTAL",
  ni      = sum(conteo$ni),
  hi      = sum(conteo$hi),
  hi_pct  = sum(conteo$hi_pct)
)

tdf_final <- bind_rows(conteo %>% mutate(Estado = as.character(Estado)), fila_total)

tdf_final %>%
  gt() %>%
  tab_header(
    title    = md("**Tabla N° 1**"),
    subtitle = md("Distribución de yacimientos según condición operativa")
  ) %>%
  cols_label(
    Estado  = "Condición Operativa",
    ni      = "Frecuencia (ni)",
    hi      = "Proporción (hi)",
    hi_pct  = "Porcentaje (hi%)"
  ) %>%
  fmt_number(columns = hi,     decimals = 4) %>%
  fmt_number(columns = hi_pct, decimals = 2) %>%
  tab_source_note(source_note = "Autor: Grupo 5") %>%
  cols_align(align = "center", columns = everything()) %>%
  tab_options(
    table.border.top.color            = "black",
    table.border.bottom.color         = "black",
    table.border.top.style            = "solid",
    table.border.bottom.style         = "solid",
    column_labels.font.weight         = "bold",
    column_labels.border.top.color    = "black",
    column_labels.border.bottom.color = "black",
    column_labels.border.bottom.width = px(2),
    heading.border.bottom.color       = "black",
    heading.border.bottom.width       = px(2),
    table_body.hlines.color           = "grey",
    table_body.border.bottom.color    = "black"
  )
Tabla N° 1
Distribución de yacimientos según condición operativa
Condición Operativa Frecuencia (ni) Proporción (hi) Porcentaje (hi%)
Activos y en Desarrollo 6584 0.8161 81.61
En etapa temprana 397 0.0492 4.92
Suspendidos o Cancelados 992 0.1230 12.30
Clausura Definitiva 84 0.0104 1.04
Reconvertido a Almacenamiento 11 0.0014 0.14
TOTAL 8068 1.0001 100.01
Autor: Grupo 5

4.Análisis Gráfico

4.1 Diagrama de Barras — Frecuencia Absoluta

colores <- colorRampPalette(c("#2E86C1", "#AED6F1"))(k)

ggplot(conteo, aes(x = Estado, y = ni, fill = Estado)) +
  geom_col(width = 0.6, color = "white") +
  geom_text(aes(label = ni), vjust = -0.4, size = 3.2, fontface = "bold") +
  scale_x_discrete(limits = orden_labels) +
  scale_fill_manual(values = colores) +
  scale_y_continuous(expand = expansion(mult = c(0, 0.15))) +
  labs(
    title   = "Gráfica N°1: Frecuencia Absoluta por Condición Operativa",
    x       = "Condición Operativa",
    y       = "Frecuencia (ni)",
    caption = paste0("n = ", format(n, big.mark = ","), " | Fuente: GOGET")
  ) +
  theme_minimal() +
  theme(legend.position = "none",
        plot.title = element_text(face = "bold"),
        axis.title = element_text(face = "bold"),
        axis.text.x = element_text(angle = 45, hjust = 1))

4.2 Diagrama de Barras — Frecuencia Relativa (Pi)

ggplot(conteo, aes(x = Estado, y = hi_pct, fill = Estado)) +
  geom_col(width = 0.6, color = "white") +
  geom_text(aes(label = paste0(hi_pct, "%")), vjust = -0.4, size = 3.2, fontface = "bold") +
  scale_x_discrete(limits = orden_labels) +
  scale_fill_manual(values = colores) +
  scale_y_continuous(expand = expansion(mult = c(0, 0.15))) +
  labs(
    title   = "Gráfica N°2: Frecuencia Relativa (Pi) por Condición Operativa",
    x       = "Condición Operativa",
    y       = "Frecuencia Relativa (%)",
    caption = paste0("n = ", format(n, big.mark = ","), " | Fuente: GOGET")
  ) +
  theme_minimal() +
  theme(legend.position = "none",
        plot.title = element_text(face = "bold"),
        axis.title = element_text(face = "bold"),
        axis.text.x = element_text(angle = 45, hjust = 1))


5.Conjetura de Modelo Geométrico

Partiendo de la Tabla de Distribución de Frecuencias (TDF) ya construida en la sección anterior — sin reordenar las categorías —, se trabaja por momentos para poder apreciar cómo se ajusta el modelo Geométrico sobre esos mismos datos.

5.1 Partiendo de la TDF: asignación de posiciones (ID)

conteo_modelo <- conteo %>%
  mutate(Estado = as.character(Estado))
conteo_modelo$ID <- 1:nrow(conteo_modelo)

conteo_modelo %>%
  select(ID, Estado, ni, hi) %>%
  gt() %>%
  tab_header(
    title    = md("**Tabla N°3**"),
    subtitle = md("TDF con posición (ID) asignada en su orden original, para el ajuste del modelo Geométrico")
  ) %>%
  cols_label(
    ID     = "Posición (ID)",
    Estado = "Condición Operativa",
    ni     = "Frecuencia (ni)",
    hi     = "Proporción (hi)"
  ) %>%
  fmt_number(columns = hi, decimals = 4) %>%
  tab_source_note(source_note = "Autor: Grupo 5") %>%
  cols_align(align = "center", columns = everything()) %>%
  tab_options(
    table.border.top.color            = "black",
    table.border.bottom.color         = "black",
    column_labels.border.top.color    = "black",
    column_labels.border.bottom.color = "black",
    column_labels.border.bottom.width = px(2),
    table_body.border.bottom.color    = "black"
  )
Tabla N°3
TDF con posición (ID) asignada en su orden original, para el ajuste del modelo Geométrico
Posición (ID) Condición Operativa Frecuencia (ni) Proporción (hi)
1 Activos y en Desarrollo 6584 0.8161
2 En etapa temprana 397 0.0492
3 Suspendidos o Cancelados 992 0.1230
4 Clausura Definitiva 84 0.0104
5 Reconvertido a Almacenamiento 11 0.0014
Autor: Grupo 5

5.2 Estimación del parámetro p (método de momentos)

Para una variable Geométrica, la media teórica es \(E(ID) = 1/p\). Se despeja \(p\) usando la media observada de las posiciones ponderada por \(hi\):

media_observada <- sum(conteo_modelo$ID * conteo_modelo$hi)
p_estimado <- 1 / media_observada

cat("Media observada de posiciones (ID ponderado por hi):", round(media_observada, 4), "\n")
## Media observada de posiciones (ID ponderado por hi): 1.3321
cat("Parámetro estimado p = 1 / media observada =", round(p_estimado, 4), "\n")
## Parámetro estimado p = 1 / media observada = 0.7507

5.3 Cálculo de probabilidades del modelo geométrico

prob_geom <- p_estimado * (1 - p_estimado)^(conteo_modelo$ID - 1)
prob_geom <- prob_geom / sum(prob_geom)

conteo_modelo$hi_modelo     <- round(prob_geom, 4)
conteo_modelo$hi_modelo_pct <- round(prob_geom * 100, 2)

df_comparativo <- conteo_modelo %>%
  select(Estado, hi_pct, hi_modelo_pct) %>%
  pivot_longer(cols = c(hi_pct, hi_modelo_pct),
               names_to = "Origen", values_to = "Valor") %>%
  mutate(Origen = ifelse(Origen == "hi_pct", "Realidad", "Modelo"))

df_comparativo$Estado <- factor(df_comparativo$Estado, levels = conteo_modelo$Estado)

5.4 Gráfica comparativa — Activos y en Desarrollo / En etapa temprana

grupo1 <- c("Activos y en Desarrollo", "En etapa temprana")

df_grupo1 <- df_comparativo %>% filter(Estado %in% grupo1)

ggplot(df_grupo1, aes(x = Estado, y = Valor, fill = Origen)) +
  geom_bar(stat = "identity", position = "dodge", color = "white") +
  geom_text(aes(label = paste0(round(Valor, 1), "%")),
            position = position_dodge(width = 0.9), vjust = -0.4, size = 3.2) +
  scale_fill_manual(values = c("Modelo" = "skyblue", "Realidad" = "#2E4053")) +
  scale_y_continuous(expand = expansion(mult = c(0, 0.15))) +
  theme_minimal() +
  theme(axis.text.x = element_text(angle = 45, hjust = 1)) +
  labs(
    title    = "Gráfica N°3: Modelo Geométrico vs Realidad — Activos y en Desarrollo / Etapa Temprana",
    subtitle = paste0("p estimado = ", round(p_estimado, 4)),
    x        = "Condición Operativa",
    y        = "Probabilidad (%)",
    fill     = "Origen"
  )

5.5 Gráfica comparativa — Suspendidos/Cancelados, Clausura Definitiva y Reconvertido a Almacenamiento

grupo2 <- c("Suspendidos o Cancelados", "Clausura Definitiva", "Reconvertido a Almacenamiento")

df_grupo2 <- df_comparativo %>% filter(Estado %in% grupo2)

ggplot(df_grupo2, aes(x = Estado, y = Valor, fill = Origen)) +
  geom_bar(stat = "identity", position = "dodge", color = "white") +
  geom_text(aes(label = paste0(round(Valor, 1), "%")),
            position = position_dodge(width = 0.9), vjust = -0.4, size = 3.2) +
  scale_fill_manual(values = c("Modelo" = "skyblue", "Realidad" = "#2E4053")) +
  scale_y_continuous(expand = expansion(mult = c(0, 0.15))) +
  theme_minimal() +
  theme(axis.text.x = element_text(angle = 45, hjust = 1)) +
  labs(
    title    = "Gráfica N°4: Modelo Geométrico vs Realidad — Suspendidos/Cancelados, Clausura y Reconversión",
    subtitle = paste0("p estimado = ", round(p_estimado, 4)),
    x        = "Condición Operativa",
    y        = "Probabilidad (%)",
    fill     = "Origen"
  )


6.Test de bondad

6.1 Test de Pearson

Fo <- conteo_modelo$hi
Fe <- conteo_modelo$hi_modelo

r_pearson <- cor(Fo, Fe) * 100
cat("Correlación de Pearson (%):", round(r_pearson, 4), "\n")
## Correlación de Pearson (%): 97.1294
plot(Fo, Fe,
     main = "Gráfica N°5: Correlación Modelo Observado y Esperado",
     xlab = "Frecuencia Observada (hi)",
     ylab = "Frecuencia Esperada (hi modelo)",
     pch  = 19,
     col  = "#2E4053")
abline(lm(Fe ~ 0 + Fo), col = "red", lwd = 2)
legend("topleft",
       legend = paste0("r = ", round(r_pearson, 2), "%"),
       bty    = "n")

6.2 Test Chi-Cuadrado

chi2_calc <- sum(((Fo - Fe)^2) / Fe)
gl        <- length(Fo) - 2
chi2_crit <- qchisq(0.95, gl)

cat("Chi-Cuadrado:", round(chi2_calc, 4), "\n")
## Chi-Cuadrado: 0.233
cat("Valor Crítico:", round(chi2_crit, 4), "\n")
## Valor Crítico: 7.8147
cat("¿El modelo geométrico es aceptado?:", chi2_calc < chi2_crit, "\n")
## ¿El modelo geométrico es aceptado?: TRUE

Tabla resumen del test

tabla_test <- data.frame(
  Variable          = "Condición Operativa",
  `Test Pearson (%)`= round(r_pearson, 2),
  `Chi Cuadrado`    = round(chi2_calc, 2),
  `Umbral de Aceptación` = round(chi2_crit, 2),
  Resultado         = ifelse(chi2_calc < chi2_crit, "Modelo Aceptado", "Modelo Rechazado"),
  check.names = FALSE
)

tabla_test %>%
  gt() %>%
  tab_header(
    title = md("**Tabla N°2: Resumen del Test de Bondad al Modelo de Probabilidad**")
  ) %>%
  tab_source_note(source_note = "Autor: Grupo 5") %>%
  cols_align(align = "center", columns = everything()) %>%
  tab_options(
    table.border.top.color            = "black",
    table.border.bottom.color         = "black",
    column_labels.border.top.color    = "black",
    column_labels.border.bottom.color = "black",
    column_labels.border.bottom.width = px(2),
    table_body.border.bottom.color    = "black"
  )
Tabla N°2: Resumen del Test de Bondad al Modelo de Probabilidad
Variable Test Pearson (%) Chi Cuadrado Umbral de Aceptación Resultado
Condición Operativa 97.13 0.23 7.81 Modelo Aceptado
Autor: Grupo 5

7.Cálculo de probabilidades

prob_activos <- conteo$hi_pct[conteo$Estado == "Activos y en Desarrollo"]
cat("Probabilidad de estar en condición 'Activos y en Desarrollo':",
    prob_activos, "%\n")
## Probabilidad de estar en condición 'Activos y en Desarrollo': 81.61 %
pozos_clausura <- sum(conteo$ni[conteo$Estado %in%
                     c("Clausura Definitiva", "Suspendidos o Cancelados")])
cat("Pozos en clausura definitiva o suspendidos/cancelados:", pozos_clausura, "\n")
## Pozos en clausura definitiva o suspendidos/cancelados: 1076

8.Conclusión

Tras excluir los registros N/S y consolidar la variable Status en 5 condiciones operativas generales, la categoría Activos y en Desarrollo concentra 81.61% de los yacimientos. Al reordenar por frecuencia descendente para el ajuste del modelo, el modelo Geométrico (p = 0.7507) obtuvo un Chi-cuadrado de 0.233 frente a un valor crítico de 7.8147, por lo que el modelo es aceptado, con una correlación de Pearson del 97.13%.