【问题标题】:How to draw lines on a plot in R?如何在R中的绘图上画线?
【发布时间】:2012-02-20 19:12:36
【问题描述】:

我需要从存储在文本文件中的数据中画线。 到目前为止,我只能在图表上绘制点,我希望将它们作为线(折线图)。

代码如下:

pupil_data <- read.table("C:/a1t_left_test.dat", header=T, sep="\t") 

max_y <- max(pupil_data$PupilLeft)

plot(NA,NA,xlim=c(0,length(pupil_data$PupilLeft)), ylim=c(2,max_y)); 

for (i in 1:(length(pupil_data$PupilLeft) - 1)) 
{
    points(i, y = pupil_data$PupilLeft[i], type = "o", col = "red", cex = 0.5, lwd = 2.0)
}

请帮我改一下这行代码:

points(i, y = pupil_data$PupilLeft[i], type = "o", col = "red")

从数据中画线。

这是文件中的数据:

PupilLeft  
3.553479    
3.539469    
3.527239    
3.613131    
3.649437    
3.632779    
3.614373    
3.605981    
3.595985    
3.630766    
3.590724    
3.626535    
3.62386 
3.619688    
3.595711    
3.627841    
3.623596    
3.650569    
3.64876 

【问题讨论】:

  • 如果要绘制lines,为什么要使用points函数?
  • plot() 函数中添加type='l' 并使用lines() aftwerards。
  • 数据:PupilLeft3.553479 3.539469 3.527239 3.613131 3.649437 3.632779 3.614373 3.605981 3.595985 3.630766 3.590724 3.626535 3.62386 3.619688 3.595711 3.627841 3.623596 3.650569 3.64876 跨度>
  • 我尝试了这两种解决方案,但是当我使用'lines()'时没有任何结果。 'plot()' fcn 中的 'type='l'' 在之后使用线条时也会发生同样的情况。
  • @user1221812:是你的循环弄乱了你的代码。请参阅我修改后的答案。

标签: r graph plot line


【解决方案1】:

默认情况下,R 将绘制单个向量作为 y 坐标,并使用序列作为 x 坐标。因此,要制作您所追求的情节,您所需要的只是:

plot(pupil_data$PupilLeft, type = "o")

您没有提供任何示例数据,但您可以通过内置的 iris 数据集看到这一点:

plot(iris[,1], type = "o")

这实际上将点绘制为线。如果您实际上得到的是没有线的点,则需要提供一个包含数据的工作示例来找出原因。

编辑:

由于循环,您的原始代码不起作用。您实际上是在要求 R 绘制一条连接 单点到自身的线,每次通过循环。下一次通过循环 R 不知道还有其他要连接的点;如果是这样,这将破坏points 的预期用途,即在现有绘图中添加点/线。

当然,将一个点与自身连接起来的线并没有真正的意义,因此它没有被绘制(或者绘制得太小而无法看到,同样的结果)。

您的示例最容易在没有循环的情况下完成:

PupilLeft <- c(3.553479 ,3.539469 ,3.527239 ,3.613131 ,3.649437 ,3.632779 ,3.614373
               ,3.605981 ,3.595985 ,3.630766 ,3.590724 ,3.626535 ,3.62386 ,3.619688
               ,3.595711 ,3.627841 ,3.623596 ,3.650569 ,3.64876)

plot(PupilLeft, type = 'o')

如果您确实需要使用循环,那么编码会变得更加复杂。一种方法是使用闭包:

makeaddpoint <- function(firstpoint){
  ## firstpoint is the y value of the first point in the series

  lastpt <- firstpoint
  lastptind <- 1

  addpoint <- function(nextpt, ...){
    pts <- rbind(c(lastptind, lastpt), c(lastptind + 1, nextpt))
    points(pts, ... )
    lastpt <<- nextpt
    lastptind <<- lastptind + 1
  }

  return(addpoint)

}

myaddpoint <- makeaddpoint(PupilLeft[1])

plot(NA,NA,xlim=c(0,length(PupilLeft)), ylim=c(2,max(PupilLeft)))

for (i in 2:(length(PupilLeft))) 
{
    myaddpoint(PupilLeft[i], type = "o")
}

然后,您可以将 myaddpoint 调用包装在 for 循环中,并使用您需要的任何测试来决定您是否会实际绘制该点。 makeaddpoint 返回的函数将为您跟踪绘图索引。

这是类 Lisp 语言的正常编程。如果您发现它令人困惑,您可以在没有闭包的情况下执行此操作,但您需要处理递增索引并在循环中“手动”存储前一个点值。

【讨论】:

  • 我必须逐个处理数据,因此我必须使用 for 循环。所以我没有数据向量,而是像pupil_data$PupilLeft[i] 这样提取的单个点。我在 OP 中提供了数据
  • @user1221812 通过遍历点并依次绘制每个点来绘制一条线根本不是它在 R 中的方式。(一方面,它的效率非常低。)如果您需要处理数据,首先这样做,然后按照 Tyler 演示的方式绘制它。
  • 它是如何完成的与我无关。我只想要一个折线图,其中线连接我用pupil_data$PupilLeft[i] 提取的点。所以我有一个点需要用线连接到另一个点,循环重复这个过程。
【解决方案2】:

经验丰富的 R 编码人员强烈反对在不需要时使用 for 循环。这是一个名为segments的向量化函数的无循环使用示例,该函数将4个向量作为参数:x0,y0,x1,y1

npups <-length(pupil_data$PupilLeft)
segments(1:(npups-1), pupil_data$PupilLeft[-npups],  # the starting points
           2:npups, pupil_data$PupilLeft[-1] )        # the ending points

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-09-04
    • 1970-01-01
    • 2021-11-29
    • 2014-07-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多