Sección 1

Ejercicio 1

a) Cread una función llamada DNA_to_RNA que haga la conversión de ADN a ARN transcrito. La entrada tiene que ser una variable de tipo carácter como “GATTACA” y la salida tiene que ser una variable de tipo carácter como “GAUUACA”.

# a) Crear función conversión ADN a ARN
DNA_to_RNA <- function(sequence){
  
  # Crear variable donde guardar la secuencia modificada
  new_sequence <- ""
  
  # Separar secuencia por cada carácter
  seq_split <- strsplit(sequence, "")[[1]]
  
  # Por cada carácter, si la letra es "T", cambiar por "U"
  for (letra in seq_split){
    if (letra == "T"){
      letra <- "U"
    }
    
    # Adjuntar la letra a la variable
    new_sequence <- paste(new_sequence, letra, sep="")
  }
  
  return(new_sequence)
}

print(DNA_to_RNA("GATTACA"))
## [1] "GAUUACA"


b) Probad la función para las cadenas de ADN “GATGTAACTTGACTACGTAAATT” y “ACGGTTCCAATGTAA”.

print(DNA_to_RNA("GATGTAACTTGACTACGTAAATT"))
## [1] "GAUGUAACUUGACUACGUAAAUU"
print(DNA_to_RNA("ACGGTTCCAATGTAA"))
## [1] "ACGGUUCCAAUGUAA"


Ejercicio 2

a) Cread una función llamada DNA_distance que calcule la distancia entre dos cadenas de ADN. La entrada tienen que ser dos cadenas de ADN (de la misma longitud) y la salida tiene que ser la distancia.

# Crear función para calcular distancia entre dos cadenas ADN
DNA_distance <- function(seq1, seq2){
  
  # Creamos una variable donde guardar el número de símbolos diferentes
  distance = 0
  
  # Si las secuencias tienen la misma longitud, separar cada una por caracteres
  if (nchar(seq1) == nchar(seq2)){
    seq_split_1 <- strsplit(seq1, "")[[1]] 
    seq_split_2 <- strsplit(seq2, "")[[1]] 
  
  # Si en la misma posición, las dos secuencias son iguales, sumamos 1 a la distancia
  for (i in 1:length(seq_split_1)){
    if (tolower(seq_split_1[i]) != tolower(seq_split_2[i])){
      distance <- distance + 1
    }
  }
  return(distance)    
  }
  
  # Si no tienen la misma longitud, devolvemos el siguiente mensaje
  else{
    return("Las secuencias no tienen la misma longitud")
  }
}


b) Probad la función para los siguientes pares de cadenas de ADN.

print(DNA_distance("GATGTAACTTGACTACGTAAATT", "GATGTAACTTGACTGCGTAAATT"))
## [1] 1
print(DNA_distance("ACGGTTCCAATGTAA", "AGGATTCCAATGTAG"))
## [1] 3


Ejercicio 3

a) Usando la función sqldf, cread una tabla con los siguientes requerimientos:

# Países con PIB menor que 800$ o mayor que 35000$ en 2007
sqldf("SELECT * FROM gapminder where year == 2007 AND (gdpPercap < 800 OR gdpPercap > 35000) ORDER BY gdpPercap ASC")
##                     country continent year lifeExp       pop  gdpPercap
## 1          Congo, Dem. Rep.    Africa 2007  46.462  64606759   277.5519
## 2                   Liberia    Africa 2007  45.678   3193942   414.5073
## 3                   Burundi    Africa 2007  49.580   8390505   430.0707
## 4                  Zimbabwe    Africa 2007  43.487  12311143   469.7093
## 5             Guinea-Bissau    Africa 2007  46.388   1472041   579.2317
## 6                     Niger    Africa 2007  56.867  12894865   619.6769
## 7                   Eritrea    Africa 2007  58.040   4906585   641.3695
## 8                  Ethiopia    Africa 2007  52.947  76511887   690.8056
## 9  Central African Republic    Africa 2007  44.741   4369038   706.0165
## 10                   Gambia    Africa 2007  59.448   1688359   752.7497
## 11                   Malawi    Africa 2007  48.303  13327079   759.3499
## 12                  Denmark    Europe 2007  78.332   5468120 35278.4187
## 13                  Austria    Europe 2007  79.829   8199783 36126.4927
## 14                  Iceland    Europe 2007  81.757    301931 36180.7892
## 15                   Canada  Americas 2007  80.653  33390141 36319.2350
## 16              Netherlands    Europe 2007  79.762  16570613 36797.9333
## 17              Switzerland    Europe 2007  81.701   7554661 37506.4191
## 18         Hong Kong, China      Asia 2007  82.208   6980412 39724.9787
## 19                  Ireland    Europe 2007  78.885   4109086 40675.9964
## 20            United States  Americas 2007  78.242 301139947 42951.6531
## 21                Singapore      Asia 2007  79.972   4553009 47143.1796
## 22                   Kuwait      Asia 2007  77.588   2505559 47306.9898
## 23                   Norway    Europe 2007  80.196   4627926 49357.1902


b) Comentad los resultados de la tabla anterior. En particular, os pedimos que expliquéis lo que veis sobre los continentes, la esperanza de vida y el PIB per cápita. Adjuntad un gráfico que muestre la relación entre PIB per cápita y la esperanza de vida e interpretadlo.

Podemos observar que los países con PIB más bajo se encuentran en el continente africano, mientras que aquellos con el PIB más alto están repartidos en Europa, Asia y América. La esperanza de vida también es significativamente menor en los países con el PIB más bajo.

# Creamos intervalos para representación en el eje x
cortes <- c(0, 1000, 4000, 8000, 12000, 16000, 25000, 40000)

intervalos <- cut(gapminder$gdpPercap, breaks = cortes, labels=c("<1000", "<4000", "<8000", "<12000", "<16000", "<25000", "<40000"))

# Gráfico relación entre PIB per cápita y esperanza de vida 
boxplot(lifeExp ~ intervalos, data=gapminder, col= palette.colors(), xlab = "PIB per cápita", ylab = "Esperanza de vida")

Existe una gran variación en los datos de esperanza de vida en aquellos países en los que el PIB per cápita es bajo. Conforme aumenta el PIB, el valor medio de esperanza de vida aumenta y se reduce la variación.

c) Usando la función dbGetQuery, cread una tabla con los siguientes requerimientos:

# Conectar comando dbConnect y especificar driver
con <- dbConnect(RSQLite::SQLite(), ":memory:")

# Definir tabla en la que guardar los datos
dbWriteTable(con, "data", gapminder)

# Mostrar medias esperanza de vida y PIB per cápita por continente en 2007
datos <- dbGetQuery(con, "SELECT continent, round(AVG(LifeExp),1) AS media_esperanza_vida, round(AVG(gdpPercap),1) AS media_PIB, stdev(LifeExp) AS stdev_esperanza FROM data where year == 2007 GROUP BY continent")

print(datos)
##   continent media_esperanza_vida media_PIB stdev_esperanza
## 1    Africa                 54.8    3089.0       9.6307807
## 2  Americas                 73.6   11003.0       4.4409476
## 3      Asia                 70.7   12473.0       7.9637245
## 4    Europe                 77.6   25054.5       2.9798127
## 5   Oceania                 80.7   29810.2       0.7290271


d) Comentad los resultados de la tabla anterior. Volved hacer un gráfico que relacione la esperanza de vida y el PIB per cápita. Relacionad lo que veis aquí con vuestro análisis en la parte b)

# Gráfico relación media esperanza de vida y PIB por continente
ggplot(datos, aes(x=continent, y=media_esperanza_vida, fill=media_PIB)) + geom_bar(stat="identity") + xlab("Continente") + ylab("Esperanza de vida") + geom_errorbar(aes(ymin=media_esperanza_vida, ymax=media_esperanza_vida + stdev_esperanza), width=0.2) + labs(fill = "Media PIB")

En la tabla, también se puede observar que la media de la esperanza de vida es mucho menor en el continente africano que, a su vez, posee un valor medio de PIB mucho menor.

Sección 2

Ejercicio 4

a) Graficad las densidades de los tiempos de vida para los ratones en condiciones normales y para los ratones a los que se les modifica la expresión de un gen. Comentad los resultados.

# Parámetros distribución Weibull ratas control
shape1 <- 5
scale1 <- 3

# Parámetros distribución Weibull ratas con expresión modificada del gen
shape2 <- 6
scale2 <- 2

rango <- 0:1000

# Crear data frame para ratas control
df_control <- data.frame(length = rweibull(rango, shape1, scale1))

# Crear data frame para ratas con expresión modificada del gen  
df_exp <- data.frame(length = rweibull(rango, shape2, scale2))

# Crear columna para identificar cada dataset 
df_control$name <- 'Control'
df_exp$name <- 'Experimento'

# Combinar data frames
df_conjunto <- rbind(df_control, df_exp)

# Representación gráfica de ambas distribuciones
ggplot(df_conjunto, aes(length, fill = name)) + geom_density(alpha=0.3) +  xlab("Años de vida") + ylab("Densidad") + ggtitle("Densidad tiempo de vida Control vs Experimento") + labs(fill = "") + xlim(0,5) + theme_pubr()

La función de densidad para las ratas con la expresión modificada del gen (experimento) está localizada sobre valores de tiempo de vida inferiores que la función para las ratas control. Aunque la altura de la función de densidad no representa la probabilidad de tener un determinado tiempo de vida, el área bajo la función sí representa la probabilidad acumulada de tener hasta dicho tiempo de vida. Por tanto, al haber un mayor área bajo la función de densidad para las ratas del experimento en valores de tiempo inferiores, estas tienen una mayor probabilidad de tener un tiempo de vida inferior al de las ratas control.

b) Calculad las probabilidades de que el tiempo de vida sea mayor que dos años para los dos tipos de ratones. Después, calculad la probabilidad de que el tiempo de vida sea inferior a un año para ambos tipos de ratones. Haced los cálculos de manera exacta y comentad los resultados.

# Probabilidad tiempo de vida mayor a 2 años (control)
1 - pweibull(2, shape1, scale1) 
## [1] 0.8766151
# Probabilidad tiempo de vida mayor a 2 años (expresión modificada gen)
1 - pweibull(2, shape2, scale2)
## [1] 0.3678794
# Probabilidad tiempo de vida inferior a 1 año (control)
pweibull(1, shape1, scale1) 
## [1] 0.00410677
# Probabilidad tiempo de vida inferior a 1 año (expresión modificada gen)
pweibull(1, shape2, scale2)
## [1] 0.01550356

Estos resultados coinciden con los observados en las funciones de densidad, ya que las ratas control tienen una mayor probabilidad de sobrevivir más de dos años, que las ratas con la expresión modificada del gen. De igual manera, se observa que las ratas del experimento tienen una mayor probabilidad de sobrevivir un año o menos.

c) A través de simulaciones, estimad la media, la varianza y los percentiles 25%, 50% y 75% del tiempo de vida para ambos tipos de ratones. Comparad los resultados de los percentiles obtenidos a través de simulaciones con los cálculos exactos obtenidos con la función qweibull. Haced 10000 simulaciones para cada tipo de ratón.

set.seed(999)

tamaño_muestra <- 10000

# Simulaciones para ratas control 
sim_control <- rweibull(tamaño_muestra, shape = shape1, scale = scale1)

# Simulaciones para ratas con expresión modificada del gen 
sim_exp <- rweibull(tamaño_muestra, shape = shape2, scale = scale2)

# Estimación media control
(mean_control <- mean(sim_control))
## [1] 2.761817
# Estimación media ratas con expresión modificada del gen
(mean_exp <- mean(sim_exp))
## [1] 1.856929
# Estimación varianza control
(var_control <- var(sim_control))
## [1] 0.400628
# Estimación varianza ratas con expresión modificada del gen
(var_exp <- var(sim_exp))
## [1] 0.1290753
# Estimación percentiles control
percentiles <- c(0.25, 0.5, 0.75)
qnorm(percentiles, mean = mean_control, sd = sqrt(var_control))
## [1] 2.334898 2.761817 3.188737
# Calcular percentiles con qweibull para el control
qweibull(percentiles, shape = shape1, scale = scale1)
## [1] 2.338319 2.787959 3.202524
# Estimación percentiles ratas con expresión modificada del gen
qnorm(percentiles, mean = mean_exp, sd = sqrt(var_exp))
## [1] 1.614605 1.856929 2.099253
# Calcular percentiles con qweibull para ratas con expresión modificada del gen
qweibull(percentiles, shape = shape2, scale = scale2)
## [1] 1.624983 1.881486 2.111896

La esperanza de supervivencia de las ratas control es mayor que las del experimento. Los percentiles, que son los valores que acumulan cierta probabilidad, también son mayores para el control. Podemos observar que los cálculos de los percentiles a partir de la simulación o de forma exacta con qweibull son muy similares, ya que el tamaño de la muestra es grande.

d) Redactad una breve reflexión sobre los aspectos éticos de utilizar animales en experimentos científicos.

La experimentación con animales se ha basado, desde sus comienzos, en la similitud fisiológica entre seres humanos y determinadas especies animales. Dicha experimentación ha permitido descubrir tecnologías o medicamentos para la curación de enfermedades en humanos, además de ayudar a prolongar la esperanza de vida. Debido a la polémica referente a la experimentación con animales en el contexto moral y ético, existen diversas tendencias al respecto. Existe una postura que defiende que su uso nunca está justificado, ni siquiera para propósitos humanos, y otra postura, que defiende que los animales se pueden usar según dispongamos. Sin embargo, la mayoría de la población y bioeticistas mantienen una postura intermedia en el que se puedan usar los animales en aquellas condiciones estrictamente necesarias. Esta postura intermedia se basa en el hecho de que no tenemos una tecnología lo suficientemente sofisticada para imitar la complejidad de las interacciones de un organismo. Por tanto, en el examen final, antes de la prueba en seres humanos, por ejemplo, de un determinado medicamento, sí defienden su uso. Afortunadamente, la tendencia actual es la reducción del número de animales, maximizando a su vez la información que obtenemos de cada uno de ellos. Además, el descubrimiento de métodos más sofisticados, basados en modelos computacionales o en cultivos celulares, también contribuye a ello. Por último, en el caso de que no exista alternativa, también se señala la importancia de mantener el bienestar del animal a lo largo de toda la experimentación. La disminución del dolor y el estrés de los animales, a su vez, es indirectamente beneficiosa para el propio experimento, ya que reduce la variabilidad de los resultados y contribuye a una mejor reproducibilidad.

Ejercicio 5

a) Si escogemos 100 individuos al azar ¿Cuál es la probabilidad de que haya al menos un individuo que tenga la enfermedad? Calculad esta probabilidad mediante un cálculo exacto y un cálculo basado en 10000 simulaciones. Comparad los resultados.

prevalencia <- 0.01 # P(Enfermo)
sensibilidad <- 0.98 # P(Test Positivo | Enfermo)
especificidad <- 0.95 # P(Test Negativo | Sano)

# P(X ≥ 1) en una muestra de 100 individuos
1 - pbinom(0, 100, prevalencia)
## [1] 0.6339677
# Simulación 10000 individuos y cálculo prevalencia
tamaño_muestra <- 10000

muestra_bin <- rbinom(tamaño_muestra, 1, prevalencia)

(prevalencia_muestra <- (table(muestra_bin)/length(muestra_bin))[2])
##      1 
## 0.0112
# P (X ≥ 1) basada en una simulación con 10000 individuos
1 - pbinom(0, 100, prevalencia_muestra)
## [1] 0.6757755

La prevalencia calculada a partir de la muestra de la simulación es muy similar a la prevalencia en la población y, por tanto, la probabilidad de encontrar al menos un individuo con enfermedad, también.

b) Si tenemos 10 individuos enfermos ¿Cuál es la probabilidad de que todas las pruebas diagnósticas sean positivas? Si tenemos 990 individuos sanos ¿Cuál es la probabilidad de que todas las pruebas diagnósticas sean negativas? Calculad las probabilidades mediante cálculos exactos y 10000 simulaciones. Comparad los resultados.

# Probabilidad 100% pruebas positivas en 10 enfermos
dbinom(10, 10, sensibilidad)
## [1] 0.8170728
# Probabilidad 100% pruebas negativas en 990 sanos
dbinom(990, 990, especificidad)
## [1] 8.83831e-23
# Número enfermos y sanos a partir de la simulación
enfermos <- table(muestra_bin)[2]
sanos <- table(muestra_bin)[1]

# Tests positivos en enfermos
muestra_enfermos_positivos <- rbinom(enfermos, 1, 0.98)

# Tests negativos en sanos
muestra_sanos_negativos <- rbinom(sanos, 1, 0.95)

# Cálculo sensibilidad a partir de la simulación
(sensibilidad_muestra <- (table(muestra_enfermos_positivos)/length(muestra_enfermos_positivos))[2])
##         1 
## 0.9821429
# Cálculo especificidad a partir de la simulación
(especificidad_muestra <- (table(muestra_sanos_negativos)/length(muestra_sanos_negativos))[2])
##         1 
## 0.9470065
# Probabilidad 100% pruebas positivas en 10 enfermos con sensibilidad calculada a partir de simulación
dbinom(10, 10, sensibilidad_muestra)
## [1] 0.8351157
# Probabilidad 100% pruebas negativas en 990 sanos con especificidad calculada a partir de simulación
dbinom(990, 990, especificidad_muestra)
## [1] 3.88524e-24


La sensibilidad y la especificidad de la prueba calculadas a partir de la simulación son muy similares a los valores de la población, ya que el tamaño de la muestra que se ha utilizado para la simulación es muy grande.

c) Supongamos que tenemos 10 individuos enfermos y 990 individuos sanos. Graficad la distribución de probabilidad del número de pruebas diagnósticas positivas para los 10 individuos enfermos y los 990 individuos sanos. Comentad los resultados.

n_enfermos = 10
n_sanos = 990

# Crear data frame con secuencia de valores para los enfermos
df_enf <- data.frame(secuencia = seq(0, n_enfermos, length.out = n_enfermos + 1))

# Añadir columna con distribución de probabilidad para pruebas positivas en 10 enfermos
df_enf$test_pos <- dbinom(seq(from=0, to=n_enfermos), n_enfermos, sensibilidad)

# Distribución de probabilidad pruebas positivas en 10 enfermos
(dist_enf_pos <- ggplot(subset(df_enf, secuencia %in% 7:10), aes(x = secuencia, y = test_pos, fill = secuencia)) + geom_bar(stat='identity') + xlab("Nº tests positivos") + ylab("Densidad de probabilidad") + ggtitle("Distribución pruebas positivas en 10 enfermos") + theme_bw() + guides(fill="none")) 

En la función de probabilidad en los 10 enfermos, las probabilidades se concentran en los valores más altos del número de enfermos ya que la sensibilidad es alta. Por tanto, existe una alta probabilidad de que, si una persona está enferma, su test sea positivo.

# Crear data frame con secuencia de valores para los sanos
df_sanos <- data.frame(secuencia = seq(0, n_sanos, length.out = n_sanos + 1))

# Añadir columna con distribución de probabilidad para pruebas positivas en 990 sanos
df_sanos$test_pos <- dbinom(seq(from=0, to=n_sanos), n_sanos, 1 - especificidad)

# Distribución de probabilidad pruebas positivas en 990 sanos
(dist_san_pos <- ggplot(subset(df_sanos, secuencia %in% 20:80), aes(x = secuencia, y = test_pos, fill = secuencia)) + geom_bar(stat='identity') + xlab("Nº tests positivos") + ylab("Densidad de probabilidad") + ggtitle("Distribución pruebas positivas en 990 sanos") + theme_bw() + guides(fill="none") + scale_x_continuous(breaks = c(seq(from=20, to=80, by=5))))

En la función de probabilidad en los 990 enfermos, los valores que toman las probabilidades más altas son valores bajos, con respecto al número de sanos. No obstante, estos valores están por encima del mínimo, ya que existe un 5% de tener un test positivo, si la persona está sana.

d) Basado en los resultados de los apartados anteriores y el hecho de que la enfermedad afecta al 1% de la población, si observamos una prueba diagnóstica positiva, justificad qué opción os parece más probable.

# Valor Predictivo Positivo P(Enfermo | Test Positivo)
(vppos <- sensibilidad * prevalencia/(sensibilidad * prevalencia + (1-especificidad) * (1-prevalencia)))
## [1] 0.1652614
# P(Sano | Test Positivo)
(p_tpos_sano <- (1 - especificidad) * (1 - prevalencia)/ (sensibilidad * prevalencia + (1 - especificidad) * (1 - prevalencia)))
## [1] 0.8347386

Ya que la probabilidad de estar sano, habiendo observado un resultado positivo, es mayor que la de estar enfermo, la opción más probable es la segunda.

  1. Es más probable que la persona no esté enferma.

Bibliografía

  • Brey, L.C., Rodríguez, K.S. Aspectos éticos de la experimentación con animales. Bioética, 27, 1-3.

  • Aranda García, A.; Pastor García, L.M. Ética de la experimentación con animales. Revista Bioética y Ciencias de la Salud, 3(4).