Biến trả lời y là hàm phi tuyến của một số biến dự đoán X (trong dữ liệu thực của tôi, phản hồi được phân phối nhị phân, nhưng ở đây tôi đang sử dụng giá trị phân phối bình thường để đơn giản). Tôi có thể mô hình hóa các mối quan hệ giữa các yếu tố dự đoán và phản hồi bằng cách sử dụng splines / smooths (ví dụ: các mô hình GAM trong mgcv
gói trong R).
Càng xa càng tốt. Tuy nhiên, mỗi phản hồi là kết quả của các quá trình phát triển theo thời gian. Nghĩa là, mối quan hệ giữa các yếu tố dự đoán X và phản ứng y thay đổi theo thời gian. Đối với mỗi phản hồi, tôi có dữ liệu cho các yếu tố dự đoán qua một số điểm thời gian xung quanh phản hồi. Đó là, có một phản hồi cho mỗi nhóm điểm thời gian (không phải là phản hồi phát triển theo thời gian).
Một số minh họa có thể hữu ích tại thời điểm này. Dưới đây là một số dữ liệu với các tham số đã biết (mã bên dưới) và sau đó được vẽ bằng ggplot2 (chỉ định phương thức GAM và mượt mà hơn), với thời gian trong các khía cạnh. Để minh họa, y là một hàm bậc hai của x1, và dấu hiệu và độ lớn của mối quan hệ này thay đổi như một hàm của thời gian.
Mối quan hệ giữa x2 và y là hình tròn, tương ứng với sự gia tăng của y với một hướng nhất định là x2. Biên độ của mối quan hệ này điều biến theo thời gian. (Được mô hình hóa trong ggplot bằng cách sử dụng một trò chơi chỉ định khối tròn "cc" mượt mà hơn).
Tôi muốn mô hình hóa sự thay đổi (phi tuyến) trong mỗi yếu tố dự đoán như là một hàm của thời gian bằng cách sử dụng một cái gì đó giống như một spline hai chiều.
Tôi đã cân nhắc sử dụng độ mịn hai chiều trong gói mgcv (đại loại như thế te(x1,t)
), ngoại trừ việc này sẽ yêu cầu dữ liệu ở dạng dài (tức là một cột các điểm thời gian). Tôi nghĩ rằng điều này là không phù hợp, bởi vì một phản hồi được liên kết với tất cả các điểm thời gian - vì vậy việc sắp xếp dữ liệu ở dạng dài (do đó sao chép cùng một phản hồi trên nhiều hàng của ma trận thiết kế) sẽ vi phạm tính độc lập của các quan sát. Dữ liệu của tôi hiện được sắp xếp với các cột (y, x1.t1, x1.t2, x1.t3, ..., x2.t1, x2.t2, ...)
và tôi nghĩ đây là định dạng phù hợp nhất.
Tôi muốn biết:
- Có cách nào tốt hơn để mô hình hóa dữ liệu này
- nếu vậy, ma trận thiết kế / công thức của mô hình sẽ như thế nào. Cuối cùng, tôi muốn ước tính các hệ số mô hình bằng cách sử dụng suy luận Bayes trong gói mcmc như JAGS, vì vậy tôi muốn biết cách viết một spline hai chiều.
Mã R để tái tạo ví dụ của tôi:
library(ggplot2)
library(mgcv)
#-------------------
# start by generating some data with known relationships between two variables,
# one periodic, over time.
set.seed(123)
nTimeBins <- 6
nSamples <- 500
# the relationship between x1, x2 and y are not linear.
# y = 0.4*x1^2 -1.2*x1 + 0.4*sin(x2) + 1.2*cos(x2)
# the relationship between x1, x2 and y evolve over time.
x1.timeMult <- cos(seq(-pi,pi,length=nTimeBins))
x2.timeMult <- cos(seq(-pi/2,pi/2,length=nTimeBins))
qplot(x=1:nTimeBins,y=x1.timeMult,geom="line") +
geom_line(aes(x=1:nTimeBins,y=x2.timeMult,colour="red")) +
guides(colour=FALSE) + ylab("multiplier")
df <- data.frame(setup=rep(NA,times=nSamples))
for (time in 1 : nTimeBins){
text <- paste('df$x1.t',time,' <- runif(nSamples,min=-3,max=3)',sep="")
eval(parse(text=text))
text <- paste('df$x2.t',time,' <- runif(nSamples,min=-pi,max=pi)',sep="")
eval(parse(text=text))
}
df$setup <- NULL
# each y is a function of x over time.
text <- 'y <- '
# replicated from above for reference:
# y = 0.4*x1^2 -1.2*x1 + 0.4*sin(x2) + 1.2*cos(x2)
for (time in 1 : nTimeBins){
text <- paste(text,'(0.4*x1.t',time,'^2-1.2*x1.t',time,') *
x1.timeMult[',time,'] + (0.4*sin(x2.t',time,') +
1.2*cos(x2.t',time,'))*x2.timeMult[',time,'] + ',sep="")
}
text <- paste(text,'rnorm(nSamples,sd=0.2)')
attach(df)
eval(parse(text=text))
df$y <- y
#-------------------
# transform into long form data for plotting:
df.long <- data.frame(y=rep(df$y,times=nTimeBins))
textX1 <- 'df.long$x1 <- c('
textX2 <- 'df.long$x2 <- c('
for (time in 1:nTimeBins){
textX1 <- paste(textX1,'x1.t',time,',',sep="")
textX2 <- paste(textX2,'x2.t',time,',',sep="")
}
textX1 <- paste(textX1,'NULL)',sep="")
textX2 <- paste(textX2,'NULL)',sep="")
eval(parse(text=textX1))
eval(parse(text=textX2))
# time stamp:
df.long$t <- factor(rep(1:nTimeBins,each=nSamples))
#-------------------
# plot relationships over time using GAM fits in ggplot:
p1 <- ggplot(df.long,aes(x=x1,y=y)) + geom_point() +
stat_smooth(method="gam",formula=y ~ s(x,bs="cs",k=4)) +
facet_wrap(~ t, ncol=3) + opts(title="x1 versus y over time")
p1
p2 <- ggplot(df.long,aes(x=x2,y=y)) + geom_point() +
stat_smooth(method="gam",formula=y ~ s(x,bs="cc",k=5)) +
facet_wrap(~ t, ncol=3) + opts(title="x2 versus y over time")
p2