为什么我的程序输出中的gr数为0?

时间:2011-09-27 03:11:47

标签: r optimization

我是R和DM / ML的新手,我写了一个小程序来试用optim函数。

我用SANN方法使用了optim。我定义了自己的gr函数,并使用control参数进行了一些配置。

问题在于,当我打印输出时,gr的计数(表示对gr函数的调用次数)为0,而对fn的调用次数是正确的。

这是我的可运行代码(我认为成本函数是无效的,所以我发布了一个简单的代码):

people = list('Seymour'='BOS',
'Franny'='DAL',
'Zooey'='CAK',
'Walt'='MIA',
'Buddy'='ORD',
'Les'='OMA')

schedulecost <- function(schedule){
    return(sum(schedule))
}

annealingOptimize <- function(domains, step=1, T=10000,costf=schedulecost){
    solution <- sample(1:9, 2 * length(people), replace=T)
    grFunction <- function(sol){
        index <- sample(c(1:length(domains$Up)), 1, replace=T)
        delta <- as.integer(runif(1,min=-step-1,max=step+1))
        newValue <- sol[index] + delta
        if (newValue > domains$Up[index]){
            newValue <- domains$Up[index]
        }
        if (newValue < domains$Down[index]){
            newValue <- domains$Down[index]
        }
        sol[index] <- newValue
        return(sol)
    }
    values <- optim(solution,costf,gr=grFunction, method='SANN',
            control=list(temp=T, REPORT=1, maxit=200, tmax=10))
    print(values)
    return(values$par)
}
domains <- list(Down=rep(1,length(people) * 2), Up=rep(9, length(people) * 2))
schedule <-annealingOptimize(domains)

输出是:

$par
 [1] 2 2 6 2 3 5 5 1 9 1 1 7

$value
[1] 44

$counts
function gradient 
     200       NA 

$convergence
[1] 0

$message
NULL

根据我的理解,gr的计数应该等于fn的计数,因为如果您通过调用{{{{}}有新候选人,则需要调用fn 1}}。

我的理解是否不正确(如果是,他们的关系是什么)或我的代码有问题。

任何人都可以提供帮助吗?

非常感谢!

更新

正如@Dwin指出的那样,在帮助文档中它说:“方法”SANN“......仅使用函数值,但相对较慢。”但在参数gr的描述中,它说:“对于“SANN”方法,它指定了一个生成新候选点的函数。“

如果你在我的gr中添加一些print语句,你会发现它实际上被非常密集地调用了。

此外,如果SANN方法只使用grFunction并且不使用gr,那么fn的句子究竟是什么意思?

1 个答案:

答案 0 :(得分:1)

研究src/main/optim.c中的代码表明SANN方法确实调用了渐变函数(当然你通过print语句确认了它),但它并不打算更新渐变计数。这是对内部SANN函数samin的调用:

   samin (npar, dpar, &val, fminfn, maxit, tmax, temp, trace, (void *)OS);
        for (i = 0; i < npar; i++)
            REAL(par)[i] = dpar[i] * (OS->parscale[i]);
        fncount = npar > 0 ? maxit : 1;
        grcount = NA_INTEGER;

我可以确认samin调用genptry调用渐变函数。

这让我觉得它是一个bug(可以报告给R开发列表,或者是R bug跟踪器),但这是一个无害的bug。正如你所指出的那样,大概是梯度(=候选点生成器)函数总是被称为完全相同的次数(好的,在设置阶段给出或取一两个)作为目标函数...(但我理解当函数没有按照文档中的说法进行操作时的混淆!)