本文介绍了在R ggplot中找到geom_smooth曲线的所有局部最大值?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要找到R中 geom_smooth()曲线的所有局部最大值.在之前的Stack Overflow中已要求这样做:

要找到一个最大值,我们使用 geom_smooth()底层的函数以获取曲线的y值.对于1000个以上的数据点,这可能是 gam();对于少于1000个的数据点,它可能是 loess().在这种情况下,它是 gam()来自 library(mgcv).要找到最大值,只需使用 which.max()进行子集设置即可.我们可以在 geom_smooth()上绘制建模的y值,以确认它们是相同的,我们的最大值由垂直线表示:

 库(mgcv)df<-df%&%;%mutate(smooth_y =预测(gam(y〜s(x,bs ="cs"),data = df)))最大<-df $ x [which.max(df $ smooth_y)]df%>%ggplot()+geom_point(aes(x = x,y = y))+geom_smooth(aes(x = x,y = y))+geom_line(aes(x = x,y = smooth_y),size = 1.5,linetype = 2,col ="red")+geom_vline(xintercept =最大值,颜色=绿色") 

到目前为止,太好了.但是,这里不止一个最大值.也许我们正试图找到正弦波的周期,以最大点之间的平均距离来衡量.我们如何确保找到该系列中的所有最大值?

我将答案发布在下面,但我想知道是否有比我使用的蛮力方法更优雅的解决方案.

解决方案

您可以使用游程长度编码找到后续点之间的差异翻转符号的点.请注意,此方法是近似的,并依赖于x的排序.您可以通过预测间距更近的x值来优化位置.

 库(tidyverse)库(mgcv)set.seed(404)df<-data.frame(x = seq(0,4 * pi,length.out = 1000),y = sin(seq(0,4 * pi,length.out = 1000))+ rnorm(100,0,1))df<-df%&%;%mutate(smooth_y =预测(gam(y〜s(x,bs ="cs"),data = df)))#游程长度编码差异的符号rle<-rle(diff(as.vector(df $ smooth_y))> 0)#计算运行起点开始<-cumsum(rle $ lengths)-rle $ lengths + 1#取rle为FALSE的点(所以差从正变到负)maxima_id<-开始[!rle $ values]#也很方便,但不是问题所在:#minima_id<-开始[rle $ values]最高<-df $ x [maxima_id]df%>%ggplot()+geom_point(aes(x = x,y = y))+geom_smooth(aes(x = x,y = y))+geom_line(aes(x = x,y = smooth_y),size = 1.5,linetype = 2,col ="red")+geom_vline(xintercept =最大值,颜色=绿色")#>使用方法='gam'和公式'y〜s(x,bs ="cs")'的`geom_smooth()` 

这篇关于在R ggplot中找到geom_smooth曲线的所有局部最大值?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-20 20:31