2012-07-06 19 views
6

Aquí está mi pequeño ejemplo: ...........filtrado condicional/subseting datos en datos de distancia lineales en r

Mark <- paste ("SN", 1:400, sep = "") 
highway <- rep(1:4, each = 100) 
set.seed (1234) 
MAF <- rnorm (400, 0.3, 0.1) 
PPC <- abs (ceiling(rnorm (400, 5, 5))) 

set.seed (1234) 
Position <- round(c(cumsum (rnorm (100, 5, 3)), 
cumsum (rnorm (100, 10, 3)), cumsum (rnorm (100, 8, 3)), 
    cumsum (rnorm (100, 6, 3))), 1) 

mydf <- data.frame (Mark, highway, Position, MAF, PPC) 

quiero para filtrar los datos que es menor que 10 para PPC al mismo tiempo mayor que 0.3 para MAF.

# filter PPC < 10 & MAF > 0.3 
filtered <- mydf[mydf$PPC < 10 & mydf$MAF > 0.3,] 

Tengo una variable de agrupamiento - carretera y cada marca tiene una posición en la carretera. Por ejemplo la carretera 1 para las primeras cinco marcas:

 1.4  7.2  15.5 13.4 19.7 
|-----|.......|.......|.....|.....| 
     "SN1" "SN2" "SN3" "SN4" "SN5" 

Ahora quiero escoger cualquier ~ 30 marcas de tal manera que están bien distribuidos en cada autopista, en función de la posición de cada carretera (considere diferente longitud de la carretera) y el mínimo distancia entre dos selecciones no es inferior a 10.

Editar: La idea (esbozo) enter image description here

lo que podía pensar un poco sobre la manera de resolver esta cuestión. Ayuda apreciada.

ediciones: Aquí algo que podía entender:

# The maximum (length) of each highway is: 
out <- tapply(mydf$Position, mydf$highway, max) 
out 
    1  2  3  4 
453.0 1012.4 846.4 597.6 

min(out) 
[1] 453 

#Total length of all highways 
totallength <- sum(out) 

# Thus average distance at which mark need to be placed: 
totallength/30 
[1] 96.98 

Por la carretera 1, las marcas teóricos que podrían estar en:

96.98, 96.98+ 96.98, 96.98+96.98+ 96.98, ........till it is less 
    than maximum (length)for highway 1. 

Así theoritically tenemos que elegir la marca en cada 96.98 . Pero las marcas colocadas en la carretera no se pueden Foud en

nota: el resultado total de selección de marcas no tiene por qué ser exactamente 30 (alrededor de 30)

+0

El problema aún no está resuelto, hágamelo saber si tiene alguna pista – shNIL

Respuesta

3

Ya que no te molesta cualquier otra columna, el código es un poco más fácil si usamos split para obtener una lista de posiciones.

filtered$highway <- factor(filtered$highway) 
positions <- with(filtered, split(Position, highway)) 

Se puede encontrar un número adecuado de marcas en cada carretera utilizando la longitud relativa de cada carretera.

highway_lengths <- sapply(positions, max) 
total_length <- sum(highway_lengths) 
n_marks_per_highway <- round(30 * highway_lengths/total_length) 

Podemos utilizar la función de cuantiles para obtener puntos de destino que estén espaciados uniformemente a lo largo de cada carretera.

target_mark_points <- mapply(
    function(pos, n) 
    { 
    quantile(pos, seq.int(0, 1, 1/(n - 1))) 
    }, 
    positions, 
    n_marks_per_highway 
) 

Para cada punto objetivo, encontramos la marca existente más cercana en la carretera.

actual_mark_points <- mapply(
    function(pos, target) 
    { 
    sapply(target, function(tgt) 
    { 
     d <- abs(tgt - pos) 
     pos[which.min(d)] 
    }) 
    }, 
    positions, 
    target_mark_points 
) 

Solo para ver si funciona, puede visualizar las marcas.

is_mark_point <- mapply(
    function(pos, mark) 
    { 
    pos %in% mark 
    }, 
    positions, 
    actual_mark_points 
) 

filtered$is.mark.point <- unsplit(is_mark_point, filtered$highway) 

library(ggplot2)  
(p <- ggplot(filtered, aes(Position, highway, colour = is.mark.point)) + 
    geom_point() 
)