# Below is an example showing how to create functions needed to generate
# MaxPro LHD manually by customLHD without using the maxproLHD function in
# the package.
compute.distance.matrix <- function(A){
s = 2
log_prod_metric = function(x, y) s * sum(log(abs(x-y)))
return (c(proxy::dist(A, log_prod_metric)))
}
compute.criterion <- function(n, p, d) {
s = 2
dim <- as.integer(n * (n - 1) / 2)
# Find the minimum distance
Dmin <- min(d)
# Compute the exponential summation
avgdist <- sum(exp(Dmin - d))
# Apply the logarithmic transformation and scaling
avgdist <- log(avgdist) - Dmin
avgdist <- exp((avgdist - log(dim)) * (p * s) ^ (-1))
return(avgdist)
}
update.distance.matrix <- function(A, col, selrow1, selrow2, d) {
s = 2
n = nrow(A)
# transform from c++ idx to r idx
selrow1 = selrow1 + 1
selrow2 = selrow2 + 1
col = col + 1
# A is the updated matrix
row1 <- min(selrow1, selrow2)
row2 <- max(selrow1, selrow2)
compute_position <- function(row, h, n) {
n*(h-1) - h*(h-1)/2 + row-h
}
# Update for rows less than row1
if (row1 > 1) {
for (h in 1:(row1-1)) {
position1 <- compute_position(row1, h, n)
position2 <- compute_position(row2, h, n)
d[position1] <- d[position1] + s * log(abs(A[row1, col] - A[h, col])) -
s * log(abs(A[row2, col] - A[h, col]))
d[position2] <- d[position2] + s * log(abs(A[row2, col] - A[h, col])) -
s * log(abs(A[row1, col] - A[h, col]))
}
}
# Update for rows between row1 and row2
if ((row2-row1) > 1){
for (h in (row1+1):(row2-1)) {
position1 <- compute_position(h, row1, n)
position2 <- compute_position(row2, h, n)
d[position1] <- d[position1] + s * log(abs(A[row1, col] - A[h, col])) -
s * log(abs(A[row2, col] - A[h, col]))
d[position2] <- d[position2] + s * log(abs(A[row2, col] - A[h, col])) -
s * log(abs(A[row1, col] - A[h, col]))
}
}
# Update for rows greater than row2
if (row2 < n) {
for (h in (row2+1):n) {
position1 <- compute_position(h, row1, n)
position2 <- compute_position(h, row2, n)
d[position1] <- d[position1] + s * log(abs(A[row1, col] - A[h, col])) -
s * log(abs(A[row2, col] - A[h, col]))
d[position2] <- d[position2] + s * log(abs(A[row2, col] - A[h, col])) -
s * log(abs(A[row1, col] - A[h, col]))
}
}
return (d)
}
n = 6
p = 2
# Find an appropriate initial temperature
crit1 = 1 / (n-1)
crit2 = (1 / ((n-1)^(p-1) * (n-2))) ^ (1/p)
delta = crit2 - crit1
temp = - delta / log(0.99)
result_custom = customLHD(compute.distance.matrix,
function(d) compute.criterion(n, p, d),
update.distance.matrix, n, p, temp = temp)
Run the code above in your browser using DataLab