Changeset 207
- Timestamp:
- 06/02/08 19:04:49 (7 months ago)
- Files:
-
- projects/AsynCluster/trunk/asyncluster/ndm/worker.py (modified) (1 diff)
- projects/AsynCluster/trunk/svpmc/model.c (modified) (3 diffs)
- projects/AsynCluster/trunk/svpmc/model.py (modified) (8 diffs)
- projects/AsynCluster/trunk/svpmc/params.py (modified) (9 diffs)
- projects/AsynCluster/trunk/svpmc/pmc.py (modified) (8 diffs)
- projects/AsynCluster/trunk/svpmc/project.py (modified) (6 diffs)
- projects/AsynCluster/trunk/svpmc/test/test_model.py (modified) (4 diffs)
- projects/AsynCluster/trunk/svpmc/test/test_params.py (modified) (9 diffs)
- projects/AsynCluster/trunk/svpmc/test/util.py (modified) (3 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
projects/AsynCluster/trunk/asyncluster/ndm/worker.py
r125 r207 91 91 Manager() 92 92 93 94 def runForeground(debug=False): 95 """ 96 Runs a child worker L{Manager} in the foreground. Useful for debugging, 97 because you can see stdout & stderr. 98 """ 99 if debug: 100 import pdb 101 try: 102 Manager() 103 except: 104 pdb.pm() 105 else: 106 Manager() projects/AsynCluster/trunk/svpmc/model.c
r205 r207 182 182 double c, cp; 183 183 const double diff = b-a; 184 const double scaleUp = 1.06; // Increase scale value to account for EXP error185 184 // Compute the scale value c as the maximum possible pdf (regular normal 186 185 // distribution) within the truncated range 187 186 if(a < 0) { 188 187 if(b > 0) { 189 // Center is within the range, so use its pdf190 c = scaleUp;188 // Center is within the range, so use the maximum pdf at center 189 c = 1.02; // Higher than 1.0 due to max EXP +error of 1.02 191 190 } else { 192 // Range is below center, so use pdf at its right edge193 c = scaleUp * EXP(-0.5*b*b);191 // Range is below center, so use maximum pdf at its right edge 192 c = 1.0625 * EXP(-0.5*b*b); // Scaled up by 1.02 / 0.96 194 193 } 195 194 } else { 196 195 // Range is above center, so use pdf at its left edge 197 c = scaleUp * EXP(-0.5*a*a);196 c = 1.0625 * EXP(-0.5*a*a); // Scaled up by 1.02 / 0.96 198 197 } 199 198 // Accept-reject sampling for the truncated normal distribution … … 315 314 // z Independent normal variates, [pn] array (updated) 316 315 // x Innovation values, [pn] array 317 // h Simulated last-sample multivariate log-volatility, [p] (overwritten)318 316 // w Wiggle value for +/- proposals (float) 319 317 // ni Number of hybrid-Gibbs iterations (int) … … 469 467 } 470 468 471 // Save the multivariate log-volatility simulated for the last time-series472 // sample in the last iteration473 for(k0=0; k0<Nt; k0++)474 H1(k0) = PA1(se[ke].h, k0);475 476 469 // Free array memory 477 470 free(xk); projects/AsynCluster/trunk/svpmc/model.py
r206 r207 89 89 self._z[member,:,:] = z 90 90 if len(self.failures) + len(self.successes) == self.m: 91 zPacked = pack.Packer(self.z)() 91 zInt = (INT_SCALE * self.z).astype('h') 92 zPacked = pack.Packer(zInt)() 92 93 k = 0 93 94 N = len(zPacked) … … 125 126 global MODEL 126 127 MODEL = modelObj 128 MODEL.z = None 127 129 128 130 def newZ(zPacked, k, N): … … 130 132 if k == 0: 131 133 CHUNKS = [] 134 MODEL.z = None 132 135 CHUNKS.append(zPacked) 133 if k == N-1: 134 MODEL.z = %f * pack.Unpacker(''.join(CHUNKS)).astype('d') 136 if k == N-1 and len(CHUNKS) == N: 137 zInt = pack.Unpacker(''.join(CHUNKS))() 138 MODEL.z = %f * zInt.astype('d') 135 139 136 140 def hybridGibbs(paramContainer): 137 return pack.Packer(*MODEL.hybridGibbs(paramContainer)) 141 if MODEL is None: 142 raise RuntimeError('No model available') 143 return pack.Packer(MODEL.hybridGibbs(paramContainer))() 138 144 139 145 def likelihood(paramContainer): 146 if MODEL is None: 147 raise RuntimeError('No model available') 148 if MODEL.z is None: 149 raise RuntimeError( 150 'Model not initialized with simulated log-volatility data') 140 151 return MODEL.likelihood(paramContainer) 141 152 … … 220 231 def unpackResult(packedResult): 221 232 if packedResult: 222 return list(pack.Unpacker(packedResult))223 233 return pack.Unpacker(packedResult)() 234 224 235 def simulationDone(result): 225 236 if result is None: 226 237 update() 227 238 return False 228 update(result[0]) 229 paramContainer.h = result[1] 239 update(result) 230 240 return True 231 241 … … 257 267 return paramContainer 258 268 269 # DEBUG 259 270 if (remote or self.remoteMode) and not local: 260 271 d = self.client.run( … … 332 343 #--- Support -------------------------------------------------------------- 333 344 334 def covarMatrix(self, cs, cr):335 """336 Returns a covariance matrix from the vector or sequence of I{cs}337 standard deviations and I{cr} cross-correlations.338 339 The I{cs} argument is in the form s0, s1,..., sp. It must have C{p}340 elements.341 342 The I{cr} argument must have C{0.5*(p**2 + p)} elements and is in the343 form r00, r01, r02,..., r0p, r11, r12,..., r1p,..., rpp344 """345 i = 0346 p = self.p347 cv = s.zeros((p, p))348 for j in xrange(p):349 cv[j,j] = cs[j]**2350 for k in xrange(j+1, p):351 cv[j, k] = cv[k, j] = cr[i] * cs[j] * cs[k]352 i += 1353 return cv354 355 345 def setParams(self, paramContainer): 356 346 """ 357 """ 358 # Set my parameters 347 Sets up array variables for an inline call made by the caller, 348 including innovations as residuals of my observations run through the 349 reversed VAR(1). 350 """ 359 351 self.setParamSequence(paramContainer.paramSequence()) 360 361 # Set up array variables for the inline call, including innovations as362 # residuals of my observations run through the reversed VAR(1)...363 352 self.x = self.var.reverse(self.a, self.b) 364 # ...concurrent cross-correlations between volatility shocks and 365 # inverse of concurrent cross-correlations between innovation shocks 366 # (we'll bail out with no result if either is invalid), and... 367 try: 368 self.rz = linalg.cholesky( 369 self.covarMatrix(self.fs, self.fr), lower=True).astype('d') 370 self.ri = linalg.inv(linalg.cholesky(self.covarMatrix( 371 s.ones(self.p), self.cr), lower=True)).astype('d') 372 except linalg.LinAlgError: 373 return 374 # ...scaling constants for multivariate normal pdf 375 self.sc = s.empty((self.p, 2)) 376 self.sc[:,0] = 1.0 / s.sqrt(1.0 - self.g**2) 377 self.sc[:,1] = s.log(s.sqrt(2*s.pi) / self.sc[:,0]) 378 353 379 354 380 355 #--- The API -------------------------------------------------------------- … … 396 371 If a L{linalg.LinAlgError} is raised due to an invalid correlation 397 372 matrix parameter, the method returns with no result. Otherwise, it 398 returns a tuple containing the following: 399 400 1. The IID normal variates underlying the simulated 401 log-volatilities after the last simulation round. 402 403 2. The multivariate log-volatility value for the last time-series 404 sample after the last simulation round. (Useful for 405 extrapolating from the fitted model.) 373 returns the IID normal variates underlying the simulated 374 log-volatilities after the last simulation round. 406 375 407 376 """ … … 410 379 # every log-volatility simulation 411 380 z = s.zeros_like(self.x) 412 # This will contain the simulated log-volatility of the last413 # time-series sample414 h = s.empty(self.p)415 381 self.inline( 416 'z', ' h', 'x', 'w', 'ni',382 'z', 'x', 'w', 'ni', 417 383 'd', 'e', 'g', 'rz', 'ri', 'sc', 418 384 w=self.wiggle, ni=self.Ni) 419 return z , h385 return z 420 386 421 387 def likelihood(self, paramContainer): projects/AsynCluster/trunk/svpmc/params.py
r206 r207 22 22 import os.path 23 23 import scipy as s 24 from scipy import linalg 24 25 from scipy.stats import distributions 25 26 … … 248 249 - A scalar I{Lj} with the log-probability density of the proposal jump 249 250 resulting in my parameters. 250 251 - A 1-D array I{h} containing the last multivariate log-volatility 252 value of any log-volatility simulation yet done on me. 253 254 """ 255 keyAttrs = {'Lx':None, 'Lp':None, 'Lj':None, 'h':None} 251 252 """ 253 keyAttrs = {'Lx':None, 'Lp':None, 'Lj':None} 256 254 257 255 … … 268 266 269 267 """ 270 keyAttrs = {'V':None}271 268 paramNames = ['dname', 'loc', 'scale', 'a', 'b'] 272 269 N_draw = 1000 273 N_attempts = 200274 270 275 271 class Constant(object): … … 318 314 319 315 def _newDraw(self): 320 D = len(self.V)321 316 rJumps = self.rdsObj.rvs(self.N_draw) 322 317 pJumps = self.rdsObj.pdf(rJumps) … … 348 343 return self.distObj.rvs(1)[0] 349 344 350 def rJump(self, startValue, vIndex): 351 """ 352 Call this method with a I{startValue} and the index I{vIndex} that 353 points to the value in my array I{V} for the jump deviation to use for 354 the jump. 345 def rJump(self, startValue, v, N_attempts=200): 346 """ 347 Call this method with a I{startValue} and the jump deviation I{v} to 348 use for the jump. 355 349 356 350 Draws a jump value from a normal distribution with a standard deviation … … 375 369 each possible jump deviation in the I{p} array of the result. 376 370 """ 377 v = self.V[vIndex]378 371 vInverse = 1.0 / v 379 for k in xrange( self.N_attempts):372 for k in xrange(N_attempts): 380 373 rJump, pJump = self._rJumpDraw() 381 374 rJump *= v … … 404 397 @ivar p: The number of time series. 405 398 406 @ivar paramNames: A list of the parameter names in sequence. 399 @ivar primaryParamNames: A list of the primary parameter names in sequence. 400 401 @ivar derivedParamNames: A list of the derived parameter names in sequence. 407 402 408 403 """ 409 404 typeChecking = True 405 N_attempts = 200 410 406 411 407 def __init__(self, p, n): … … 420 416 return array 421 417 418 def covarMatrix(self, cs, cr): 419 """ 420 Returns a covariance matrix from the vector or sequence of I{cs} 421 standard deviations and I{cr} cross-correlations. 422 423 The I{cs} argument is in the form s0, s1,..., sp. It must have C{p} 424 elements. 425 426 The I{cr} argument must have C{0.5*(p**2 + p)} elements and is in the 427 form r00, r01, r02,..., r0p, r11, r12,..., r1p,..., rpp 428 """ 429 i = 0 430 p = len(cs) 431 cv = s.zeros((p, p)) 432 for j in xrange(p): 433 cv[j,j] = cs[j]**2 434 for k in xrange(j+1, p): 435 cv[j, k] = cv[k, j] = cr[i] * cs[j] * cs[k] 436 i += 1 437 return cv 438 439 def derivedParams(self, paramContainer): 440 """ 441 Sets derived parameters in the supplied I{paramContainer} based on its 442 primary parameters, unless there is an error in generating the derived 443 parameters. 444 445 Returns C{True} if everything went OK, C{False} if not. 446 """ 447 # Concurrent cross-correlations between volatility shocks and inverse 448 # of concurrent cross-correlations between innovation shocks 449 try: 450 rz = linalg.cholesky(self.covarMatrix( 451 paramContainer.fs, paramContainer.fr), lower=True) 452 ri = linalg.inv(linalg.cholesky(self.covarMatrix( 453 s.ones(self.p), paramContainer.cr), lower=True)) 454 except linalg.LinAlgError: 455 return False 456 paramContainer.rz = rz 457 paramContainer.ri = ri 458 # Scaling constants for multivariate normal pdf 459 sc = s.empty((self.p, 2)) 460 sc[:,0] = 1.0 / s.sqrt(1.0 - paramContainer.g**2) 461 sc[:,1] = s.log(s.sqrt(2*s.pi) / sc[:,0]) 462 paramContainer.sc = sc 463 return True 464 422 465 def new(self): 423 466 """ 424 467 Returns a new parameter container with values intialized from a random 425 468 draw of my priors. 426 """ 427 Lp = 0 428 paramContainer = ParameterContainer(paramNames=self.paramNames) 429 for name in self.paramNames: 430 priorFlexArray = getattr(self, name) 431 paramArray = priorFlexArray.call('rvs') 432 Lp += s.log(priorFlexArray.call('pdf', paramArray)).sum() 433 setattr(paramContainer, name, paramArray) 469 470 The method will generate derived parameters based on the primary 471 parameter values, repeating as needed to get primary values that 472 work. The derived values are included in the returned parameter 473 container. 474 """ 475 paramContainer = ParameterContainer( 476 paramNames=self.primaryParamNames+self.derivedParamNames) 477 for k in xrange(self.N_attempts): 478 Lp = 0 479 for name in self.primaryParamNames: 480 priorFlexArray = getattr(self, name) 481 paramArray = priorFlexArray.call('rvs') 482 setattr(paramContainer, name, paramArray) 483 Lp += s.log(priorFlexArray.call('pdf', paramArray)).sum() 484 if self.derivedParams(paramContainer): 485 break 486 else: 487 raise ValueError( 488 "Couldn't generate a valid set of derived parameters") 434 489 paramContainer.Lp = Lp 435 490 paramContainer.Lj = 0 # There was no jump 436 491 return paramContainer 437 492 438 def proposal(self, paramContainer, v Index, vWeights):493 def proposal(self, paramContainer, v): 439 494 """ 440 495 Returns a new instance of L{ParameterContainer} with a random-walk 441 proposal based on the supplied I{paramContainer}, my priors, the jump 442 deviation defined at the I{vIndex} position of my 1-D array of jump 443 deviations, and a 1-D array I{vWeights} of mixture weights for the jump 444 deviations in the jump distribution. 496 proposal based on the supplied I{paramContainer}, my priors, and the 497 supplied jump deviation I{v}. 445 498 446 499 The returned parameter container object will have new values of I{Lp} 447 500 and I{Lj} corresponding to the proposal. 448 501 449 The value of I{Lj} is computed for each parameter element from a jump 450 distribution that is a mixture of normal distributions. Each of the 451 normals has a standard deviation defined by one element of my jump 452 deviation array with a corresponding mixture weight in the supplied 453 I{vWeights} array. 502 The value of I{Lj} is computed for each parameter element from a normal 503 jump distribution whose width is proportional to the jump deviation 504 I{v} and the width of the parameter's prior distribution. 505 506 The method will generate derived parameters based on the primary 507 parameter values of the proposal, repeating as needed to get primary 508 values that work. The derived values are included in the returned 509 parameter container. 454 510 """ 455 511 if self.typeChecking and \ … … 458 514 "You must supply a ParameterContainer as the first "+\ 459 515 "argument, not a '%s'" % type(paramContainer)) 460 newVersion = ParameterContainer(paramNames=self.paramNames) 461 Lp, Lj = 0, 0 462 # Define a 1-D array holding the probability density for each jump, 463 # joint across all parameters. Since the densities will be scaled by 464 # the weight for each jump deviation, just start the array with the 465 # weights. 466 for name in self.paramNames: 467 priorsFA = getattr(self, name) 468 startValues = getattr(paramContainer, name) 469 jumpsFA = priorsFA.call('rJump', startValues, vIndex) 470 setattr(newVersion, name, jumpsFA.x) 471 Lp += s.log(jumpsFA.px).sum() 472 Lj += s.log(jumpsFA.pJump).sum() 516 newVersion = ParameterContainer( 517 paramNames=self.primaryParamNames + self.derivedParamNames) 518 for k in xrange(self.N_attempts): 519 Lp, Lj = 0, 0 520 # Define a 1-D array holding the probability density for each jump, 521 # joint across all parameters. Since the densities will be scaled 522 # by the weight for each jump deviation, just start the array with 523 # the weights. 524 for name in self.primaryParamNames: 525 priorsFA = getattr(self, name) 526 startValues = getattr(paramContainer, name) 527 jumpsFA = priorsFA.call( 528 'rJump', startValues, v, N_attempts=self.N_attempts) 529 setattr(newVersion, name, jumpsFA.x) 530 Lp += s.log(jumpsFA.px).sum() 531 Lj += s.log(jumpsFA.pJump).sum() 532 if self.derivedParams(newVersion): 533 break 534 else: 535 raise ValueError( 536 "Couldn't generate a valid set of derived parameters") 473 537 newVersion.Lp = Lp 474 538 newVersion.Lj = Lj projects/AsynCluster/trunk/svpmc/pmc.py
r206 r207 157 157 self.pm = projectManager 158 158 self.mm = projectManager.mgr 159 self.V = projectManager.V 159 160 self.queue = projectManager.queue 160 161 self.resampler = Resampler(logWeights=True) … … 171 172 def proposals(self, *args): 172 173 """ 173 Call this method with a 1-D FlexArray of parameter containers and a n174 integer index of a particular jump deviation, and it will generate175 p roposals from the existing parameters.174 Call this method with a 1-D FlexArray of parameter containers and a 175 jump deviation, and it will generate proposals from the existing 176 parameters. 176 177 177 178 Call it with just an integer number of proposals, and it will generate 178 179 new ones directly from the priors. 179 180 180 Runs a log-volatility simulation for each proposal via the model 181 manager, which constructs a 3-D array of the normal variates underlying 182 the entire set of simulations. 183 184 Returns a deferred that fires when all the log-volatility simulations 185 are done. The deferred fires with a 1-D FlexArray of the proposals 186 along with an equal-length 1-D bool array of True/False values 187 indicating which of them resulted in valid log-volatility simulations. 188 """ 189 def simulationDone(success): 190 if success: 191 print vIndex, 192 else: 193 print ".", 194 I.append(success) 195 196 def allDone(null): 197 return XP, s.array(I) 198 199 dList = [] 200 I = [] 181 Returns a 1-D FlexArray of parameter containers embodying the 182 proposals. 183 """ 201 184 if len(args) == 2: 202 185 new = False 203 X, v Index= args186 X, v = args 204 187 N = len(X) 205 188 else: 206 189 new = True 207 190 N = args[0] 208 vIndex = "+"209 191 XP = params.FlexArray(N) 210 192 for k in xrange(N): … … 212 194 proposalPC = self.pm.priors.new() 213 195 else: 214 proposalPC = self.pm.priors.proposal( 215 X[k], vIndex, self.allocator.W) 196 proposalPC = self.pm.priors.proposal(X[k], v) 216 197 XP[k] = proposalPC 217 d = self.mm.zSimulation(proposalPC, k) 198 return XP 199 200 def simulations(self, X): 201 """ 202 Runs a log-volatility simulation for each parameter container supplied 203 in the 1-D FlexArray I{X}. The simulations are run via the model 204 manager, which constructs a 3-D array of the normal variates underlying 205 the entire set of simulations. 206 207 Returns a deferred that fires when all the log-volatility simulations 208 are done. 209 """ 210 def simulationDone(success): 211 if success: 212 print "+", 213 else: 214 print ".", 215 216 dList = [] 217 for k, Xk in enumerate(X): 218 d = self.mm.zSimulation(Xk, k) 218 219 d.addCallback(simulationDone) 219 220 d.addErrback(self._oops, k=k) 220 221 dList.append(d) 221 return defer.DeferredList(dList).addCallback(allDone) 222 223 def weights(self, XP, vIndex): 222 d = defer.DeferredList(dList) 223 d.addCallback(lambda _: self.mm.nextIteration()) 224 d.addErrback(self._oops) 225 return d 226 227 def weights(self, XP, v): 224 228 """ 225 229 Returns a deferred that fires with a 1-D array of log importance 226 weights for the p roposals suppliedin the 1-D FlexArray I{XP}.230 weights for the parameter proposals in the 1-D FlexArray I{XP}. 227 231 228 232 The importance weights are to be combined with those from other calls … … 241 245 for x in ('Lx', 'Lp', 'Lj')]) 242 246 else: 243 info = ""244 247 L = -s.inf 245 print "%6.4f\t%+12.2f\t%s" % (self.pm.V[vIndex], L, info) 248 if L < 0: 249 print "%6.4f" % v 250 else: 251 print "%6.4f\t%+12.2f\t%s" % (v, L, info) 246 252 return L 247 253 … … 250 256 dList = [self.mm.likelihood(XPk).addCallback(weight) for XPk in XP] 251 257 return defer.gatherResults(dList).addCallback(lambda W: s.array(W)) 252 258 253 259 @defer.deferredGenerator 254 260 def run(self, N_iter): … … 266 272 267 273 """ 268 def gotTheseWeights(Wv, I, Iv):269 """270 Returns a 1-D weights array of the same length as this allocation's271 length, with infinitely negative values except for the valid272 weights supplied in I{Wv}.273 """274 W = -s.inf * s.ones(len(I))275 W[Iv] = Wv276 return W277 278 274 X = None 279 275 if self.socket: … … 286 282 for i in xrange(N_iter): 287 283 print "\n%03d\n%s" % (i+1, "-"*100) 288 self.mm.nextIteration()289 284 if X is None: 290 print "Generating %d proposals from priors:" % N_members291 285 # No existing members, generate proposals directly from the 292 # priors 293 wfd = defer.waitForDeferred(self.proposals(N_members)) 286 # priors and simulate log-volatilities for them 287 print "Generating %d proposals from priors " % N_members +\ 288 "and simulating log-volatilities for them" 289 wfd = defer.waitForDeferred( 290 self.queue.call(self.proposals, N_members)) 294 291 yield wfd 295 XP, validXP = wfd.getResult() 296 else: 297 print "Generating %d proposals from previous population:" \ 298 % N_members 299 # Regular iteration, use proposals generated from the last 300 # iteration's members 301 dList, resultList = [], [] 292 XP = wfd.getResult() 293 wfd = defer.waitForDeferred(self.simulations(XP)) 294 yield wfd 295 wfd.getResult() 296 else: 297 # Regular iteration, simulate log-volatilities for the last 298 # iteration's members and use proposals generated from those 299 # members 300 print "\nSimulating log-volatilities for the previous "+\ 301 "population and generating %d proposals " % N_members +\ 302 "from the population:" 303 resultList = [] 304 dList = [self.simulations(X)] 302 305 for vIndex, I, d in self.allocator.assembler(resultList): 303 d.addCallback(lambda _: self.proposals(X[I], vIndex)) 304 dList.append(d) 306 d.addCallback( 307 lambda _: 308 self.queue.call(self.proposals, X[I], self.V[vIndex])) 309 d.addErrback(self._oops, vIndex=vIndex) 310 dList.append(d) 311 # Record the previous iteration's members while the nodes work on 312 # generating the proposals and simulations for the current iteration... 313 if i > 0: 314 self.pm.writeParams(X) 305 315 wfd = defer.waitForDeferred(defer.DeferredList(dList)) 306 316 yield wfd 307 317 wfd.getResult() 308 XP , validXP = resultList318 XP = resultList[0] 309 319 print "\n" 310 320 # Evaluate the proposals 311 321 dList, resultList = [], [] 312 322 for vIndex, I, d in self.allocator.assembler(resultList): 313 Iv = validXP[I].nonzero()[0] 314 d.addCallback(lambda _: self.weights(XP[I][Iv], vIndex)) 315 d.addCallback(gotTheseWeights, I, Iv) 323 d.addCallback(lambda _: self.weights(XP[I], self.V[vIndex])) 316 324 d.addErrback(self._oops, vIndex=vIndex) 317 325 dList.append(d) 318 # Record the previous iteration's members while the nodes work on319 # evaluating the valid proposals for the current iteration...320 if X is not None:321 self.pm.writeParams(X)322 # "Wait" here for all the proposals to be evaluated323 326 wfd = defer.waitForDeferred(defer.DeferredList(dList)) 324 327 yield wfd … … 332 335 self.allocator.updateAllocations(I0[I1]) 333 336 else: 337 # No valid parameters, start over 338 X = None 334 339 self.allocator.updateAllocations() 335 340 wfd = defer.waitForDeferred(self.pm.done()) projects/AsynCluster/trunk/svpmc/project.py
r206 r207 70 70 iteration. 71 71 72 @ivar paramNames: A list of the names of parameter arrays in the parameter73 sequences used in the project.72 @ivar paramNames: A list of the names of arrays in the parameter containers 73 used in the project for both primary and secondary parameters. 74 74 75 75 @ivar D: The number of jump deviations used by the D-kernel PMC … … 91 91 'm': 'member', 92 92 } 93 94 93 def __init__(self, specFile, ncFile="svpmc.nc", m=1000, readOnly=False): 95 94 self.m = m … … 224 223 pa[j,k] = params.Prior(**kw) 225 224 226 self.p aramNames = []225 self.primaryParamNames = [] 227 226 titles, dimensions = [], [] 228 227 self.paramInfo = {} … … 236 235 constructPriors(priorSpec, shape) 237 236 titles.append(title) 238 self.paramNames.append(name) 239 self.priors.paramNames = self.paramNames 237 self.primaryParamNames.append(name) 238 self.priors.primaryParamNames = self.primaryParamNames 239 self.derivedParamNames = [] 240 for name, sourceParams, description in self.tables['derivation']: 241 self.derivedParamNames.append(name) 242 self.priors.derivedParamNames = self.derivedParamNames 243 self.paramNames = self.primaryParamNames + self.derivedParamNames 240 244 return titles, dimensions 241 245 … … 254 258 obs.long_name = "Observations, %d time series " % self.p +\ 255 259 "with %d samples each" % self.n 256 # Last-Sample Log-Volatility257 logVol = cdf.createVariable(258 "log_volatility", 'f', ('iteration', 'member', 'series'))259 logVol.long_name = "Last Sample of Simulated Log-Volatilities"260 260 # Parameters 261 for k, name in enumerate(self.p aramNames):261 for k, name in enumerate(self.primaryParamNames): 262 262 pDim = ['iteration', 'member'] + pDims[k] 263 263 param = cdf.createVariable(name, 'f', tuple(pDim)) 264 264 param.long_name = pTitles[k] 265 # Log-Likelihood 266 L = cdf.createVariable(" log_likelihood", 'f', ('iteration', 'member'))265 # Log-Likelihood, log-density of priors and jumps 266 L = cdf.createVariable("Lx", 'f', ('iteration', 'member')) 267 267 L.long_name = "Log-Likelihood of Observations Given Parameters" 268 L = cdf.createVariable("Lp", 'f', ('iteration', 'member')) 269 L.long_name = "Log-Density of Parameters from Prior Distributions" 270 L = cdf.createVariable("Lj", 'f', ('iteration', 'member')) 271 L.long_name = "Log-Density of Proposal Jumps" 268 272 # Done setting up, save what we've got thus far 269 273 cdf.sync() … … 279 283 "Each iteration record must have %d parameters" % self.m) 280 284 # Write the parameters to their variables 281 for name in self.p aramNames:285 for name in self.primaryParamNames: 282 286 var = self.cdf.variables[name] 283 287 # Iterate over a 1-D FlexArray of the population's parameter arrays 284 288 for member, paramArray in enumerate(getattr(parameters, name)): 285 289 var[self.iteration, member, :] = paramArray.astype('f') 286 # Write the l ast sample's multivariate log-volatility valuefor each290 # Write the log-volatility, prior and jump log-density values for each 287 291 # population member 288 var = self.cdf.variables['log_volatility'] 289 for member, h in enumerate(parameters.h): 290 var[self.iteration, member, :] = h.astype('f') 291 # Write the log-volatility value for each population member 292 var = self.cdf.variables['log_likelihood'] 293 var[self.iteration, :] = parameters.Lx.astype('f') 292 for name in ('Lx', 'Lp', 'Lj'): 293 var = self.cdf.variables[name] 294 var[self.iteration, :] = getattr(parameters, name).astype('f') 294 295 # Done writing this iteration of the CDF record 295 296 self.cdf.sync() projects/AsynCluster/trunk/svpmc/test/test_model.py
r205 r207 346 346 347 347 class Test_Model_misc(BaseCase): 348 def test_covarMatrix(self):349 def tryCoeffs(cs, cr, x):350 x = s.array(x)351 modelObj.y = s.empty((x.shape[0], 100))352 y = modelObj.covarMatrix(cs, cr)353 self.failUnlessEqual(y.shape, x.shape)354 self.failUnless(355 s.absolute(y-x).max() < 1E-8,356 "Generated array \n%s\n != \n%s" % (y, x))357 358 modelObj = model.Model()359 tryCoeffs([1.0], [], [[1.0]])360 tryCoeffs([1.0, 1.0], [0.2], [[1.0, 0.2], [0.2, 1.0]])361 tryCoeffs([2, 3], [0], [[4.0, 0.0], [0.0, 9.0]])362 tryCoeffs([3, 4], [0.5], [[9.0, 6.0], [6.0, 16.0]])363 tryCoeffs(364 [3, 4, 5], [0.1, 0.2, 0.3],365 [[9.0, 1.2, 3.0], [1.2, 16.0, 6.0], [3.0, 6.0, 25.0]])366 367 348 def test_support_uniform(self): 368 349 code = """ … … 384 365 X1(k) = truncnorm(a, b); 385 366 """ 386 Ns = 100 367 Ns = 10000 387 368 ranges = ((-1, +1), (-0.5, +1.5), (1.0, 2.0), (3.0, 5.0)) 388 369 fig = self.fig … … 752 733 ('g', -0.9, +0.9)] 753 734 fig = self.fig 754 spNumberBase = 100*len(paramInfoList) + 11735 spNumberBase = 100*len(paramInfoList) + 21 755 736 for j, paramInfo in enumerate(paramInfoList): 756 737 paramName = paramInfo[0] … … 761 742 Lx[k] = modelObj.inlineDirect( 762 743 modelObj.code['likelihood'], **inlineVars) 763 sp = fig.add_subplot(spNumberBase+ j)744 sp = fig.add_subplot(spNumberBase+2*j) 764 745 sp.plot(values, Lx, '.') 765 746 sp.set_title("Parameter '%s'" % paramName) 747 sp = fig.add_subplot(spNumberBase+2*j+1) 748 Lx_max = Lx.max() 749 sp.plot(values, s.exp(Lx-Lx_max)) 750 sp.set_title("Parameter '%s'" % paramName) 766 751 inlineVars[paramName] = originalParamValue 752 753 def test_Lx_vs_z(self): 754 wiggle = 1.0 755 eValue = 0.90 756 Ns, Ni, Nr = 1000, 40, 200 757 758 Lx = s.empty(Nr) 759 modelObj = model.Model() 760 761 inlineVars = self._inlineVars(wiggle, eValue, Ni) 762 for zReal, zSim, hReal, hSim in self._hybridGibbs(Ns, 1, inlineVars): 763 pass 764 765 fig = self.fig 766 zErrorList = [0.0005, 0.001, 0.01] 767 spNumberBase = 100*len(zErrorList) + 11 768 for j, zError in enumerate(zErrorList): 769 for k in xrange(Nr): 770 inlineVars['z'] = ( 771 zSim + zError*2*(s.rand(1, Ns) - 0.5)).reshape((1, 1, Ns)) 772 Lx[k] = modelObj.inlineDirect( 773 modelObj.code['likelihood'], **inlineVars) 774 sp = fig.add_subplot(spNumberBase+j) 775 sp.hist(Lx) 776 sp.set_title("Range (+/-) of zError: %f" % zError) 767 777 768 778 def test_optimize_Ni(self): projects/AsynCluster/trunk/svpmc/test/test_params.py
r196 r207 222 222 class Test_Prior(util.TestCase): 223 223 def setUp(self): 224 self.V = s.array([1.0, 0.1, 0.01]) 225 self.p = params.Prior(dname='norm', loc=1, scale=1, D=3, Df=0.1) 224 self.p = params.Prior(dname='norm', loc=1, scale=1) 226 225 self.p.N_draw = 10 227 226 self.pdf = self.p.rdsObj.pdf … … 235 234 self.failUnless(s.equal(s.array([p.pdf(x) for x in X]), 0.5).all()) 236 235 237 def _checkDraw(self, r v, pV):236 def _checkDraw(self, rJump, pJump): 238 237 pdf = self.p.rdsObj.pdf 239 for k, v in enumerate(self.V): 240 self.failUnlessAlmostEqual(pdf(rv/v)/v, pV[k], 5) 238 self.failUnlessAlmostEqual(pdf(rJump), pJump, 5) 241 239 242 240 def test_newDraw(self): … … 249 247 def test_rJumpDraw(self): 250 248 for k in xrange(103): 251 r v, pV= self.p._rJumpDraw()252 self._checkDraw(r v, pV)249 rJump, pJump = self.p._rJumpDraw() 250 self._checkDraw(rJump, pJump) 253 251 254 252 def test_rJump(self): 255 253 for startValue in s.linspace(-1, +3, 10): 256 for vIndex, v in enumerate(self.V): 257 jumpObj = self.p.rJump(startValue, vIndex) 258 print "\n", vIndex, v 254 for v in (0.1, 0.001, 0.0001): 255 jumpObj = self.p.rJump(startValue, v) 259 256 jumpValue = jumpObj.x - startValue 260 257 rv = jumpValue / v 261 print jumpValue, rv, jumpObj.pV[vIndex] 262 self.failUnlessAlmostEqual(self.pdf(rv)/v, jumpObj.pV[vIndex]) 263 print "OK" 264 265 266 class Test_PriorContainer(util.TestCase): 258 self.failUnlessAlmostEqual(self.pdf(rv)/v, jumpObj.pJump) 259 260 261 class Test_PriorContainer_misc(util.TestCase): 267 262 MPC = util.Mock_ParameterContainer 268 V = s.array([1.0, 0.1, 0.01])269 263 270 264 def setUp(self): 271 265 self.priorContainer = params.PriorContainer( 272 self.MPC.p, self.MPC.N , self.V)266 self.MPC.p, self.MPC.N) 273 267 self.priorContainer.typeChecking = False 274 self.priorContainer.paramNames = self.MPC.paramNames 275 kw = {'dname':'norm', 'loc':0, 'V':self.V} 276 for i, name in enumerate(self.priorContainer.paramNames): 268 self.priorContainer.primaryParamNames = util.PRIMARY_PARAM_NAMES 269 self.priorContainer.derivedParamNames = util.DERIVED_PARAM_NAMES <
