在 R 中沿直线的点和曲线之间绘制一条垂线

问题描述

我希望在 R 中计算一条线的中点与其上方的曲线之间的距离,但在数学上很密集。我的曲线看起来都像下面代码显示的那样:

Curve <- data.frame(X = c(NA,NA,4.9046,6.1424,7.275,8.5851,10.0373,11.9981,13.7726,15.0731,16.0664,18.1945,21.2666,24.2093,26.7119,28.8037,30.7135,32.1351,33.1982,34.2341,35.7587,37.2147,38.4303,39.625,40.4596,42.0938,42.7428,42.7593,43.5085,43.7419,43.5989,44.0841,NA),Y = c(NA,-9.9938,-7.4596,-4.8647,-2.2903,0.3158,2.9302,5.7262,8.7033,11.8007,14.9847,16.7225,16.7813,15.6921,14.2964,11.5579,8.2378,5.183,1.5938,-2.0712,-5.195,-7.1447,-9.0446,-11.1269,-13.0979,-15.3295,-17.1898,-19.4376,-21.4781,-23.8426,-25.6343,fan_line = 1:42)    

我能够在第一个和最后一个 xy 坐标之间画一条线并找到该线的中点(如下图所示)。从这个中点我现在需要构建一条从中点延伸到曲线的垂直线,并在该点提取 xy 坐标。我不知道这是如何完成的。

enter image description here

如果相关,我所有的绘图都是在 ggplot 中完成的,但主要是我有兴趣提取与图像中显示的中点垂直的 XY 坐标(曲线的第一个和最后一个 xy 坐标之间的中点),因此值而不是比绘图本身。

我之前一直根据中间 X 坐标(忽略 NA 值)计算曲线的中间 x 和 y 坐标,但这根本不是我想要的。

最终,我想获得一个值,即图像中虚线的距离除以垂直线的长度。

请原谅我对数学的无知

编辑:正如 Limey 指出的,一个点有任意数量的垂直线。我的意思是从我画的虚线的中点垂直。

Edit2:抱歉我不清楚我在找什么。基本上,我想最终获得类似于下图中红线的东西(原谅 Microsoft Paint 工作)。

enter image description here

解决方法

approx() 函数允许您找到与给定 x 坐标对应的 y 坐标,例如:

approx(Curve$X,Curve$Y,mean(range(Curve$X,na.rm=TRUE)) )
# $x
# [1] 24.49435
# 
# $y
# [1] 16.65724

然而,您似乎想在曲线上找到与端点之间的线垂直的点的中点。为此,您可以通过连接端点的直线的梯度旋转曲线,使直线变平,使用上述方法,然后以相反的方向旋转。执行此操作的代码是:

library(lava)

Ends <- Curve[Curve$X %in% range(Curve$X,na.rm=TRUE),]

theta <- atan(diff(Ends$Y)/diff(Ends$X))

rotCurve <- rotate2(as.matrix(Curve)[,1:2],theta)
rotEnds <- rotate2(as.matrix(Ends)[,theta)

rotPoint <- approx(rotCurve[,1],rotCurve[,2],mean(rotEnds[,1]) )

Point <- rotate2(matrix(c(rotPoint$x,rotPoint$y),ncol=2),-theta)
#         [,1]     [,2]
# [1,] 33.39819 4.490086

使用快速绘图来验证它看起来像您的图表

ggplot() + geom_line(aes(x=X,y=Y),Curve) + geom_line(aes(x=X,data=Ends,lty=2) + 
  geom_line(aes(x=c(mean(Ends$X),Point[1]),y=c(mean(Ends$Y),Point[2])),colour='red') + coord_equal()

Output plot