How to generate multiple matrix in R - r

I have gotten two lists of values in R.
daily_max_car: (List 1)
21 21 22 22 22 22 21
daily_0.8: (List 2)
16 17 17 17 18 17 17
Trying to write a For Loop in R-Studio to generate multiple matrix by using the one of the values from these two lists (One by One).
Here is the code I have been using to generate one matrix!
Lambda <- 21 (From List 1)
Mue <- 4
Rho <- Lambda/Mue
N <- 16 (From List 2)
All of these four parameters will be used in the "calculatewq" Function.
calculatewq <- function(c)
{....Some thing happening }
##Create Matrix
matrix1 <- matrix(0,Lambda,4)
matrix1[,1] <- 1:Lambda
### Create a column of matrix with repeated "N"
rep.row<-function(x,y)
{matrix(rep(x,each=y),nrow=y)}
created_mar_1 <- rep.row(N,Lambda)
car_n<- created_mar_1-matrix1[,1]
created_mar_3 <- rep.row(69*60*24,Lambda)
## Add into Matrix
for (i in 1:Lambda)
{matrix1[i,2] <- calculatewq(i)[2]
matrix1[i,3] <- calculatewq(i)[5]
matrix1[,4] = car_n*created_mar_3}`
Once I change one of the parameters it will generate a new matrix.
Thus, how can I write a for loop to generate multiple matrix while I am putting different value in Lambda and N.
Thank you so much!
Sampson

I removed for loop inside calculatewq function. Please make sure you needed a for loop in it.
myfun <- function(Lambda, N, mu )
{
# browser()
var1 <- seq_len( Lambda )
var2 <- ( rep( N, each = Lambda) ) - var1
var3 <- rep( 69*60*24, each = Lambda )
var4 <- var2 * var3
fun_vals <- do.call( 'rbind',
lapply( var1, function( x ) calculatewq( x, Lambda = Lambda, N = N, mu = mu ) ) )
mat <- matrix( NA, nrow = Lambda, ncol = mu )
mat[, 1] <- var1
mat[, 2] <- fun_vals[, 'Wq']
mat[, 3] <- fun_vals[, 'customer_serviced']
mat[, 4] <- var4
return(mat)
}
calculatewq <- function( x, Lambda, N, mu )
{
# browser()
Rho <- Lambda / mu
p0_inv <- ( Rho^x * (1-(( Rho/x )^( N-x+1)))) / (factorial( x ) * ( 1 - ( Rho / x ) ) )
p0_inv <- p0_inv + ( Rho^x) / factorial( x )
P0 <- 1/p0_inv
Lq <- ( Rho^(x+1)) * (1-((Rho/x)^(N-x+1))-((N-x+1)*(1-(Rho/x))*((Rho/x)^(N-x))))*P0/(factorial(x-1)*(x-Rho)^2)
Wq <- 60*Lq/Lambda
Ls <- Lq + Rho
Ws <- 60*Ls/Lambda
PN <- (Rho^N)*P0/(factorial(x)*x^(N-x))
customer_serviced <- (1 - PN)*100
a <- cbind( Lq, Wq, Ls, Ws, customer_serviced )
return(a)
}
mu <- 4
res <- Map( myfun,
list( 21 ,21, 22, 22 ,22, 22 ,21 ),
list( 16, 17, 17, 17, 18, 17 ,17 ),
mu)
head( res[[1]])
# [,1] [,2] [,3] [,4]
# [1,] 1 42.184874 19.04762 1490400
# [2,] 2 38.241748 38.09526 1391040
# [3,] 3 33.339271 57.13862 1291680
# [4,] 4 26.014138 75.70348 1192320
# [5,] 5 16.339462 89.88989 1092960
# [6,] 6 9.121053 96.32498 993600

daily_max_car <- list(21,21,22,22,22,22,21)
daily_0.8 <- list(16,17,17,17,18,17,17)
myfunction <- function(Lambda, N){
Mue <- 4
Rho <- Lambda/Mue
df <- as.data.frame(matrix(0, ncol = 4, nrow = Lambda))
names(df) <- c("A","B","C","D")
df[,1] <- 1:Lambda
df[,2] <- N
df[,3] <- df[,1] - df[,2]
df[,4] <- 69*60*24
return(df)
}
myfunction(21,16)
result <- mapply(myfunction, daily_max_car, daily_0.8)
Result

Lambda <- 21
Mue <- 4
Rho <- Lambda/Mue
N <- 19
matrix1 <- matrix(0,Lambda,4)
matrix1[,1] <- 1:Lambda
rep.row<-function(x,y)
{
matrix(rep(x,each=y),nrow=y)
}
created_mar_1 <- rep.row(N,Lambda)
car_n<- created_mar_1-matrix1[,1]
created_mar_3 <- rep.row(69*60*24,Lambda)
calculatewq(7)
calculatewq <- function(c)
{
P0inv <- (Rho^c*(1-((Rho/c)^(N-c+1))))/(factorial(c)*(1-(Rho/c)))
for (i in 1:c-1)
{
P0inv = P0inv + (Rho^i)/factorial(i)
}
P0 = 1/P0inv
Lq = (Rho^(c+1))*(1-((Rho/c)^(N-c+1))-((N-c+1)*(1-(Rho/c))*((Rho/c)^(N- c))))*P0/(factorial(c-1)*(c-Rho)^2)
Wq = 60*Lq/Lambda
Ls <- Lq + Rho
Ws <- 60*Ls/Lambda
PN <- (Rho^N)*P0/(factorial(c)*c^(N-c))
customer_serviced <- (1 - PN)*100
a <- cbind(Lq,Wq,Ls,Ws,customer_serviced)
return(a)
}
for (i in 1:Lambda)
{
matrix1[i,2] <- calculatewq(i)[2]
matrix1[i,3] <- calculatewq(i)[5]
matrix1[,4] = car_n*created_mar_3
}

Related

Error in while (e_i$X1 < 12 | e_i$X2 < 12) { : argument is of length zero

In an earlier question (R: Logical Conditions Not Being Respected), I learned how to make the following simulation :
Step 1: Keep generating two random numbers "a" and "b" until both "a" and "b" are greater than 12
Step 2: Track how many random numbers had to be generated until it took for Step 1 to be completed
Step 3: Repeat Step 1 and Step 2 100 times
res <- matrix(0, nrow = 0, ncol = 3)
for (j in 1:100){
a <- rnorm(1, 10, 1)
b <- rnorm(1, 10, 1)
i <- 1
while(a < 12 | b < 12) {
a <- rnorm(1, 10, 1)
b <- rnorm(1, 10, 1)
i <- i + 1
}
x <- c(a,b,i)
res <- rbind(res, x)
}
head(res)
[,1] [,2] [,3]
x 12.14232 12.08977 399
x 12.27158 12.01319 1695
x 12.57345 12.42135 302
x 12.07494 12.64841 600
x 12.03210 12.07949 82
x 12.34006 12.00365 782
Question: Now, I am trying to make a slight modification to the above code - Instead of "a" and "b" being produced separately, I want them to be produced "together" (in math terms: "a" and "b" were being produced from two independent univariate normal distributions, now I want them to come from a bivariate normal distribution).
I tried to modify this code myself:
library(MASS)
Sigma = matrix(
c(1,0.5, 0.5, 1), # the data elements
nrow=2, # number of rows
ncol=2, # number of columns
byrow = TRUE) # fill matrix by rows
res <- matrix(0, nrow = 0, ncol = 3)
for (j in 1:100){
e_i = data.frame(mvrnorm(n = 1, c(10,10), Sigma))
e_i$i <- 1
while(e_i$X1 < 12 | e_i$X2 < 12) {
e_i = data.frame(mvrnorm(n = 1, c(10,10), Sigma))
e_i$i <- i + 1
}
x <- c(e_i$X1, e_i$X2 ,i)
res <- rbind(res, x)
}
res = data.frame(res)
But this is producing the following error:
Error in while (e_i$X1 < 12 | e_i$X2 < 12) { : argument is of length
zero
If I understand your code correctly you are trying to see how many samples occur before both values are >=12 and doing that for 100 trials? This is the approach I would take:
library(MASS)
for(i in 1:100){
n <- 1
while(any((x <- mvrnorm(1, mu=c(10,10), Sigma=diag(0.5, nrow=2)+0.5))<12)) n <- n+1
if(i==1) res <- data.frame("a"=x[1], "b"=x[2], n)
else res <- rbind(res, data.frame("a"=x[1], "b"=x[2], n))
}
Here I am assigning the results of a mvrnorm to x within the while() call. In that same call, it evaluates whether either are less than 12 using the any() function. If that evaluates to FALSE, n (the counter) is increased and the process repeated. Once TRUE, the values are appended to your data.frame and it goes back to the start of the for-loop.
Regarding your code, the mvrnorm() function is returning a vector, not a matrix, when n=1 so both values go into a single variable in the data.frame:
data.frame(mvrnorm(n = 1, c(10,10), Sigma))
Returns:
mvrnorm.n...1..c.10..10...Sigma.
1 9.148089
2 10.605546
The matrix() function within your data.frame() calls, along with some tweaks to your use of i, will fix your code:
library(MASS)
Sigma = matrix(
c(1,0.5, 0.5, 1), # the data elements
nrow=2, # number of rows
ncol=2, # number of columns
byrow = TRUE) # fill matrix by rows
res <- matrix(0, nrow = 0, ncol = 3)
for (j in 1:10){
e_i = data.frame(matrix(mvrnorm(n = 1, c(10,10), Sigma), ncol=2))
i <- 1
while(e_i$X1[1] < 12 | e_i$X2[1] < 12) {
e_i = data.frame(matrix(mvrnorm(n = 1, c(10,10), Sigma), ncol=2))
i <- i + 1
}
x <- c(e_i$X1, e_i$X2 ,i)
res <- rbind(res, x)
}
res = data.frame(res)

How can I modify my code to include loop?

I am trying to create a function that examines how variables with different distributions influence OLS results. I have created two DVs (y1 and y2) but would like to expand this to include five or so. I am trying to change my code to include a loop so I do not have to copy and paste this multiple times, but I am not having much luck. Any suggestions would be greatly appreciated.
library(psych)
library(arm)
library(plyr)
library(fBasics)
regsim <- function(iter, n) {
ek1 <- rnorm(n, 0, 1)
ek2 <- rnorm(n, 0, 5)
x <- rnorm(n, 0, .5)
y1 <- .3*x + ek1
y2 <- .3*x + ek2
#y1
lm1 <- lm(y1 ~ x)
bhat1 <- coef (lm1)[2]
sehat1 <- se.coef (lm1) [2]
skewy1 <- skew(y1)
stdevy1 <- stdev(y1)
#y2
lm2 <- lm(y2 ~ x)
bhat2 <- coef (lm2)[2]
sehat2 <- se.coef (lm2) [2]
skewy2 <- skew(y2)
stdevy2 <- stdev(y2)
results <- c(bhat1, sehat1, stdevy1, skewy1,
bhat2, sehat2, stdevy2, skewy2)
names(results) <- c('b1', 'se1', 'sdy1', 'skewy1',
'b2', 'se2', 'sdy2', 'skewy2')
return(results)
}
iter <-1000
n <-500
results <- NULL
sims <-ldply(1:iter, regsim, n)
sims$n <- n
results <- rbind(results, sims)
Another option...
regsim <- function(n=100,num.y=5,sd=c(1:5)){
if(length(sd) != num.y){stop('length of sd must match number of dependent vars')
} else {
ldply(1:num.y,function(x){
e <- rnorm(n,0,sd=sd[x])
x <- rnorm(n,0,5)
y <- 0.3*x + e
out <- lm(y~x)
b1 <- coef(out)[2]
int <- coef(out)[1]
data.frame(b1=b1,int=int)
})
}
}
regsim(num.y=10,sd=c(1:10))
b1 int
1 0.30817303 0.0781049
2 0.38681600 -0.3359067
3 0.24560773 -0.0277561
4 0.08032659 0.1877233
5 0.39873955 -0.6027522
6 0.21729930 0.7384340
7 0.33761456 -0.1053028
8 0.26502006 -0.1851552
9 0.15452261 -1.6334873
10 -0.10496863 -0.3225169
This will allow you to specify the number of dependent variables and the SD for each error term. You can then use replicate to repeat the function for the desired number of replications.
replicate(10,regsim(),simplify = F)
[[1]]
b1 int
1 0.3047779 -0.01984306
2 0.3133198 -0.20458410
3 0.2833979 -0.25307502
4 0.3066878 -0.03235019
5 0.1374949 0.10958616
[[2]]
b1 int
1 0.2902103 -0.12683502
2 0.3499006 0.06691437
3 0.1949797 -0.14371830
4 0.2358269 0.53117467
5 0.2869511 0.16281380
[[3]]
b1 int
1 0.2952211 0.05905549
2 0.2367774 0.02862166
3 0.0896778 -0.08467935
4 0.2352622 -0.20835837
5 0.3149963 0.07042032
[[4]]
b1 int
1 0.2946468 -0.08266406
2 0.3322577 0.17558135
3 0.2200087 -0.25778150
4 0.1822915 0.34962679
5 0.2442479 0.34433656
[[5]]
b1 int
1 0.2882853 0.12677506
2 0.3455534 -0.27885958
3 0.2981193 0.04598347
4 0.3380173 0.05243198
5 0.2148643 -0.09631672
[[6]]
b1 int
1 0.2962269 0.03743759
2 0.2979327 -0.12830803
3 0.3352781 -0.03935422
4 0.2584965 -0.05924351
5 0.2856802 0.03430055
[[7]]
b1 int
1 0.2968077 -0.10300109
2 0.2954560 0.25979902
3 0.3276077 -0.07001758
4 0.1825841 0.13508932
5 0.4302788 -0.13951914
[[8]]
b1 int
1 0.2992147 0.02084806
2 0.2765976 0.07277813
3 0.2469616 0.44580403
4 0.2601966 -0.09849855
5 0.2679183 0.50501652
[[9]]
b1 int
1 0.2963905 0.03308366
2 0.3356783 -0.06080088
3 0.3199835 0.22533444
4 0.3546083 -0.26909478
5 0.3536241 -0.19795094
[[10]]
b1 int
1 0.3100336 -0.05228032
2 0.4076447 -0.18715063
3 0.3436858 -0.37518649
4 0.4569368 -0.09114672
5 0.3255668 -0.18738138
How about this:
n <- 1000
x <- rnorm(n, 0, .5)
fun_reg <- function(n, ek_mu, ek_sd, x){
s <- list() # list to collect results for output
ek <- rnorm(n, ek_mu, ek_sd)
y <- .3*x + ek
m <- lm(y ~ x)
s$bhat <- coef(m)[2]
s$sehat <- arm::se.coef(m)[2]
s$skewy <- psych::skew(y)
s$stdevy <- fBasics::stdev(y)
return(s)
}
purrr::map_dfr(c(1, 5, 10, 20, 50), ~fun_reg(n, 0, ., x))
Edit:
This now has 500 observations each and the regression is repeated with 1000 draws for each value of the standard deviation. A variable ek_sd has been added to the final output, to reflect with which standard deviation the values were arrived at. Note that x is not redrawn for each iteration, but I'm not entirely sure, that that is what you want. If you want x to be redrawn at each iteration, move it inside the function.
n <- 500
x <- rnorm(n, 0, .5)
fun_reg <- function(n, ek_mu, ek_sd, x){
s <- list()
ek <- rnorm(n, ek_mu, ek_sd)
y <- .3*x + ek
m <- lm(y ~ x)
s$ek_sd <- ek_sd
s$bhat <- coef(m)[2]
s$sehat <- arm::se.coef(m)[2]
s$skewy <- psych::skew(y)
s$stdevy <- fBasics::stdev(y)
return(s)
}
intr <- unlist(lapply(c(1, 5, 10, 20, 50), rep, 1000))
purrr::map_dfr(intr, ~fun_reg(n, 0, ., x))
This reduces the package reliance to just psych::skew and an optional ggplot2 call:
library(psych)
regsim <- function(n, eks) {
x <- rnorm(n, 0, .5)
ek <- sapply(eks, function(x) rnorm(n, 0, x))
y <- 0.3 * x + ek
lms <- lm(y ~ x)
data.frame(b_hat = lms[['coefficients']][2,],
int = lms[['coefficients']][1, ],
skew_y = psych::skew(y),
se_hat = unlist(lapply(summary(lms), function(lst) lst[[4]][2,2]), use.names = FALSE),
sd_y = apply(y, 2, sd),
sd_eks = eks
)
}
iter <-1000
n <-500
eks_sd = c(1,5)
# do the simulations and make them into a nice data.frame
sims <- replicate(iter, regsim(n, eks_sd), simplify = FALSE)
results <- do.call(rbind, sims)
#next parts are optional
results$iter_id <- rep(seq_len(iter), each = length(eks_sd))
tibble::as_tibble(results)
# Random graph because everyone loves graphs
library(ggplot2)
ggplot(results, aes(x = iter_id, y = int)) + geom_point() + facet_grid(vars(sd_eks))
The main thing is that lm can take multiple y arguments. That's why we we create a matrix of ek using sapply.

Manipulating sub matrices in R

Nh<-matrix(c(17,26,30,17,23, 17 ,24, 23), nrow=2, ncol=4); Nh
Sh<-matrix(c(8.290133, 6.241174, 6.096808, 7.4449672, 6.894924, 7.692115,
4.540521, 7.409122), nrow=2, ncol=4); Sh
NhSh<-as.matrix(Nh*Sh); NhSh
rh<-c( 0.70710678, 0.40824829, 0.28867513, 0.22360680, 0.18257419,
0.15430335, 0.13363062, 0.11785113, 0.10540926, 0.09534626); rh
pv <- c()
for (j in 1:2) {
for (i in 1:4) {
pv <- rbind(pv, NhSh[j,i]*rh)
}
}
pv
row.names(pv) <- rep(c(1:2), each = 4)
lst<-lapply(split(seq_len(nrow(pv)), as.numeric(row.names(pv))), function(i)
pv[i,])
data<-40
nlargest <- function(x, data)
{
res <- order(x)[seq_len(data)];
pos <- arrayInd(res, dim(x), useNames = TRUE);
list(values = pv[res], position = pos)
}
out <- lapply(lst, nlargest, data = 40)
In continuation of above code Is there any brief way of repeating the following steps for each out$’k’$position for k in 1:2?
s1<-c(1,1,1,1); ch<-c(5,7,10,5); C<-150; a<-out$'1'$position
for (j in a[40:1, "row"] )
{
s1[j] <- s1[j]+1;
cost1 <- sum(ch*s1);
if (cost1>=C) break
}
s1; cost1
#Output [1] 5 6 6 5
# [1] 152
I have to get 2 values for 's' and 'cost' for out$k$position. I tried
mat = replicate (2,{x = matrix(data = rep(NA, 80), ncol = 2)}); mat
for (k in 1:2)
{
mat[,,k]<-out$'k'$position
}
mat
Error in mat[, , k] <- out$k$position :number of items to replace is not a multiple of replacement length
for (k in 1:2)
{
for (j in mat[,,k][40:1] ) {
s[j] <- s[j]+1
cost <- sum(ch*s)
if (cost>=C) break
}
}
s; cost
Error : Error in s[j] <- s[j] + 1 : NAs are not allowed in subscripted assignments
Please anyone help in resolving these errors.
We could apply the function directly by looping over the list. Note that each element of the list is a matrix
sapply(lst, is.matrix)
# 1 2
#TRUE TRUE
so, there is no need to unlist and create a matrix
out <- lapply(lst, nlargest, data = 40)
-checking with the OP's results
out1 <- nlargest(sub1, 40)
identical(out[[1]], out1)
#[1] TRUE
Update2
Based on the second update, we need to initialize 'cost' and 'sl' with the same length as 'k' elements. Here, we initialize 'sl' as a list of vectors
sl <- rep(list(c(1, 1, 1, 1)), 2)
C <- 150
cost <- numeric(2)
for (k in 1:2){
for (j in mat[,,k][40:1, 1] ) {
sl[[k]][j] <- sl[[k]][j]+1
cost[k] <- sum(ch*sl[[k]])
if (cost[k] >=C) break
}
}
sl
#[[1]]
#[1] 5 7 6 4
#[[2]]
#[1] 6 5 5 7
cost
#[1] 154 150

Applying a function to elements of each row and then summarising

I have a question on manipulating data in data.frame.
Essentially I have a large data set - abbreviated version below:
structure(list(nm_mean = c(194213914.326, 194213914.326, 194213914.326,
194213914.326, 194213914.326, 217947112.739), nm_se = c(9984735.05918367,
9984735.05918367, 9984735.05918367, 9984735.05918367, 9984735.05918367,
11010386.0760204), alpha = c(193.197697846336, 214.592588477741,
240.246557258741, 258.116959355425, 282.560024775668, 306.610038660465
), beta = c(61526.2664158025, 57950.9563448233, 56085.1512614369,
52919.4794239927, 51483.4591654126, 50405.8186695088)), .Names = c("nm_mean",
"nm_se", "alpha", "beta"), row.names = c(NA, 6L), class = "data.frame")
I want to use rbeta to generate probabilities using the beta distribution and alpha and beta as the parameters
Similarly I want to use rnorm to generate random numbers using the normal distribution with nm_mean and nm_se as the mean and sd.
I then want to multiply the rbeta values generated by the rnorm values and extract the 50th, 25th and 75th quantile back into the dataframe
So as an example for row 1
x <- rbeta(1000,193.1977,61526.27)
y <- rnorm(1000,194213914,9984735)
z <- x*y
dat$ce <- quantile(z,0.5)
dat$ll <- quantile(z,0.25)
dat$ul <- quantile(z,0.975)
In essence i get a ce, ll and ul for product of the rbeta and rnorm appended back to the database.
Motivated by #HackR's code, what I think is a functional vectorized version:
set.seed(42)
n <- 1000
nrows <- nrow(dat)
rn <- matrix(rnorm(nrows * n, dat$nm_mean, dat$nm_se), ncol = nrows, byrow = TRUE)
rb <- matrix(rbeta(nrows * n, shape1 = dat$alpha, shape2 = dat$beta),
ncol = nrows, byrow = TRUE)
cbind(dat,
structure(t(apply(rn * rb, 2, function(z) quantile(z, c(0.5, 0.25, 0.975)))),
.Dimnames = list(NULL, c("ce", "ll", "ul"))))
# nm_mean nm_se alpha beta ce ll ul
# 1 194213914 9984735 193.1977 61526.27 608455.3 570100.5 710373.6
# 2 194213914 9984735 214.5926 57950.96 715305.0 677754.3 856570.7
# 3 194213914 9984735 240.2466 56085.15 825143.7 778351.2 979361.1
# 4 194213914 9984735 258.1170 52919.48 943261.4 895832.6 1091899.3
# 5 194213914 9984735 282.5600 51483.46 1054514.3 995640.8 1226176.4
# 6 217947113 11010386 306.6100 50405.82 1312325.0 1247030.8 1515630.5
This is vectorized solution based on my conversation with #thelatemail:
n <- 1000
grp <- nrow(dat)
z <- with(dat, rnorm(grp*n, nm_mean, nm_se) * rbeta(grp*n, alpha, beta) )
m <- 1
for(i in 1:nrow(dat)){
dat$ce[i] <- quantile(z[m:(i*1000)],0.5)
dat$ll[i] <- quantile(z[m:(i*1000)],0.25)
dat$ul[i] <- quantile(z[m:(i*1000)],0.975)
m <- m + 1000
}
A less vectorized solution is:
for(i in 1:nrow(dat)){
x <- rbeta(1000, shape1 = dat$alpha[i], shape2 = dat$beta[i])
y <- rnorm(n=1000,dat$nm_mean[i],dat$nm_se[i])
z <- x*y
dat$ce[i] <- quantile(z,0.5)
dat$ll[i] <- quantile(z,0.25)
dat$ul[i] <- quantile(z,0.975)
}
dat
nm_mean nm_se alpha beta ce ll ul
1 194213914 9984735 193.1977 61526.27 607563.9 573229.9 713057.2
2 194213914 9984735 214.5926 57950.96 712268.5 674826.3 836950.8
3 194213914 9984735 240.2466 56085.15 823322.9 777482.8 981156.7
4 194213914 9984735 258.1170 52919.48 937331.2 884945.0 1095876.3
5 194213914 9984735 282.5600 51483.46 1059980.4 1003596.4 1225615.6
6 217947113 11010386 306.6100 50405.82 1316733.1 1250190.1 1515185.0

I am getting Issue of "incorrect number of subscripts on matrix"?

I am getting problem of "incorrect number of subscripts on matrix" for long, Please help me. I am trying to find the bug but unable to find, my data set is huge but i am using smaller initial data for program run. I have tried my best but all in vain. The error comes in the last lines of code. I am new to coding so plz excuse my mistake in indentation.
########### inputs
#Y <- as.matrix(read.table("data2.dat"));
#X <- as.matrix(read.table("data1.dat"));
###########
# smaller X and Y for initial code run.
X <- matrix(c(71,22,53,14,75,68,74,93,72),9,1)
Y <- matrix(c(7,1,4,1,7,6,6,8,5),9,1)
########### Constant
Xlen <- length(X[,1]) #### rows of X
Yhat <- as.matrix(mat.or.vec(Xlen,1))
error <- as.matrix(mat.or.vec(Xlen,1))
Rmax <- 30
Z <- as.matrix(cbind(X,Y))
Zlen <- length(Z[1,]) #### columns of Z
P <- as.matrix(mat.or.vec(1,Rmax))
U <- as.matrix(mat.or.vec(1,Rmax)) # mu calculation
lambda <- as.matrix(mat.or.vec(1,Rmax)) # lambda calculation
C <- as.matrix(mat.or.vec(Zlen,Rmax))
R <- 0
sigma <- 0
beta <- as.matrix(mat.or.vec(1,Zlen))
Zp <- mat.or.vec(1,Zlen)
V1 <- 0
V2 <- 0
V3 <- 0
Pz <- 0
Dmin <-0
Dind <-0
Pmax <-0
Pind <-0
r <- 0.4
alpha <- 4/(r^2)
P_mat <- 10^4 * diag(2)
gamma <- as.matrix(mat.or.vec(2,Rmax))
w <- as.matrix(mat.or.vec(2,Rmax))
Xe <- as.matrix(cbind(1,X))
#####
for (i in 1:Xlen)
{
if (i==1)
{R <- R+1 ; C[,R] <- Z[i,] ; P[R] <- 1; Yhat <- Y[i,]}
else
{V1 <- sum(Z[i,]^2)
sigma <- sigma + sum(Z[i-1,]^2)
beta <- beta + Z[i-1,]
V2 <- sum(Z[i,]*t(beta))
Pz <- (i-1)/((i-1)*(V1+1)+(sigma-(2*V2)))
for (j in 1:R)
{V3 <- sum((Z[i,]-Z[i-1,])^2);P[j] <- ((i-1)*P[j])/((i-2)+(P[j])+(P[j]*V3))}
dist <- as.matrix(mat.or.vec(1,R))
for (k in 1:R)
{dist[k] <- abs(sqrt(sum((Z[i,]-C[,k])^2)))}
Dmin <- min(dist)
Dind <- which.min(dist)
Pmax <- max(P)
Pind <- which.max(P)
if (r > Dmin/(1-(Pz/Pmax)) && Pz > Pmax)
{C[,Dind] <- Z[i,]; P[Dind] <- Pz}
if (r < (Dmin/(1-(Pz/Pmax))) && Pz > Pmax && R< Rmax)
{R <- R+1; C[,R] <- Z[i,]; P[R] <- Pz}
for(n in 1:R)
{U[,n] <- exp(-alpha*(X[i]-C[1,n])^2)}
for(n in 1:R)
{lambda[,n] <- U[,n]/sum(U)}
A1 <- as.matrix(P_mat%*%Xe[i,]%*%lambda)
B1 <- as.matrix(t(lambda)%*%Xe[i,])
C1 <- as.matrix(diag(Rmax))
D1 <- as.matrix(P_mat)
E1 <- as.matrix(B1%*%D1%*%t(B1))
F1 <- C1+E1
gamma <- A1%*%solve(F1)
P_mat <- (diag(2)%*%gamma%*%t(lambda)%*%Xe[i,])%*%P_mat
G1 <- as.matrix(lambda%*%t(Xe[i,]%*%w))
H1 <- as.matrix(Y[i,])
I1 <- as.vector(H1-G1)
J1 <- I1*gamma
w <- w + J1; #as.matrix(I1%*%gamma)
K1 <- Xe[i,]%*%w
L1 <- lambda%*%t(K1)
here comes error at Yhat
Yhat[i,] <- L1
#error[i,] <- Y[i,]-Yhat[i,]
#b <- b+1
}
}
#Yhat <- as.vector(Yhat)
#plot(Y,type="l",col="red")
#lines(Yhat,col="green")
#plot(Yhat)
#plot(error)
Without going through all of your code, let's see what happens to Yhat:
First, you make it a matrix:
Yhat <- as.matrix(mat.or.vec(Xlen,1))
> Yhat
[,1]
[1,] 0
[2,] 0
[3,] 0
[4,] 0
[5,] 0
[6,] 0
[7,] 0
[8,] 0
[9,] 0
In the first iteration of your loop for (i in 1:Xlen) you assign Y[i,] to Yhat:
if (i==1)
{R <- R+1 ; C[,R] <- Z[i,] ; P[R] <- 1; Yhat <- Y[i,]}
At that point, Y[i,] is 7. Yhat is no longer a matrix, now it's of type numeric. Therefore, Yhat[i,] <- L1 throws an error.

Resources