def test_recursion(self): """ Make sure things work as expected with a chain of locators/grids/locators. This makes a Cartesian-like reactor out of unit cubes. The origin is in the center of the central cube radially and the bottom axially due to the different way steps and bounds are set up. """ core = MockArmiObject() assem = MockArmiObject(core) block = MockArmiObject(assem) # build meshes just like how they're used on a regular system. coreGrid = grids.CartesianGrid.fromRectangle( 1.0, 1.0, armiObject=core ) # 2-D grid # 1-D z-mesh assemblyGrid = grids.Grid( bounds=(None, None, numpy.arange(5)), armiObject=assem ) # pins sit in this 2-D grid. blockGrid = grids.CartesianGrid.fromRectangle(0.1, 0.1, armiObject=block) coreLoc = grids.CoordinateLocation(0.0, 0.0, 0.0, None) core.spatialLocator = coreLoc assemblyLoc = grids.IndexLocation(2, 3, 0, coreGrid) assem.spatialLocator = assemblyLoc blockLoc = grids.IndexLocation(0, 0, 3, assemblyGrid) block.spatialLocator = blockLoc pinIndexLoc = grids.IndexLocation(1, 5, 0, blockGrid) pinFree = grids.CoordinateLocation(1.0, 2.0, 3.0, blockGrid) assert_allclose(blockLoc.getCompleteIndices(), numpy.array((2, 3, 3))) assert_allclose(blockLoc.getGlobalCoordinates(), (2.0, 3.0, 3.5)) assert_allclose(blockLoc.getGlobalCellBase(), (1.5, 2.5, 3)) assert_allclose(blockLoc.getGlobalCellTop(), (2.5, 3.5, 4)) # check coordinates of pins in block assert_allclose( pinFree.getGlobalCoordinates(), (2.0 + 1.0, 3.0 + 2.0, 3.5 + 3.0) ) # epic assert_allclose( pinIndexLoc.getGlobalCoordinates(), (2.0 + 0.1, 3.0 + 0.5, 3.5) ) # wow # pin indices should not combine with the parent indices. assert_allclose(pinIndexLoc.getCompleteIndices(), (1, 5, 0))
def construct(self, cs, bp, reactor, geom=None): """Build a core/IVS/EVST/whatever and fill it with children.""" from armi.reactor import reactors # avoid circular import runLog.info("Constructing the `{}`".format(self.name)) if geom is not None: gridDesign = geom.toGridBlueprint("core") else: gridDesign = bp.gridDesigns[self.gridName] spatialGrid = gridDesign.construct() container = reactors.Core(self.name) container.setOptionsFromCs(cs) container.spatialGrid = spatialGrid container.spatialGrid.armiObject = container reactor.add(container) # need parent before loading assemblies spatialLocator = grids.CoordinateLocation(self.origin.x, self.origin.y, self.origin.z, None) container.spatialLocator = spatialLocator if armi.MPI_RANK != 0: # on non-master nodes we don't bother building up the assemblies # because they will be populated with DistributeState. # This is intended to optimize speed and minimize ram. return None self._loadAssemblies(cs, container, gridDesign, gridDesign.gridContents, bp) summarizeMaterialData(container) self._modifyGeometry(container, gridDesign) container.processLoading(cs) return container
def construct(self, cs, bp, reactor, geom=None): """Build a core/IVS/EVST/whatever and fill it with children.""" from armi.reactor import reactors # avoid circular import runLog.info("Constructing the `{}`".format(self.name)) # TODO: We should consider removing automatic geom file migration. if geom is not None and self.name == "core": gridDesign = geom.toGridBlueprints("core")[0] else: if not bp.gridDesigns: raise ValueError( "The input must define grids to construct a reactor, but " "does not. Update input." ) gridDesign = bp.gridDesigns.get(self.gridName, None) system = self._resolveSystemType(self.typ)(self.name) # TODO: This could be somewhere better. If system blueprints could be # subclassed, this could live in the CoreBlueprint. setOptionsFromCS() also isnt # great to begin with, so ideally it could be removed entirely. if isinstance(system, reactors.Core): system.setOptionsFromCs(cs) # Some systems may not require a prescribed grid design. Only try to use one if # it was provided if gridDesign is not None: spatialGrid = gridDesign.construct() system.spatialGrid = spatialGrid system.spatialGrid.armiObject = system reactor.add(system) # need parent before loading assemblies spatialLocator = grids.CoordinateLocation( self.origin.x, self.origin.y, self.origin.z, None ) system.spatialLocator = spatialLocator if armi.MPI_RANK != 0: # on non-master nodes we don't bother building up the assemblies # because they will be populated with DistributeState. return None # TODO: This is also pretty specific to Core-like things. We envision systems # with non-Core-like structure. Again, probably only doable with subclassing of # Blueprints self._loadAssemblies(cs, system, gridDesign, gridDesign.gridContents, bp) # TODO: This post-construction work is specific to Cores for now. We need to # generalize this. Things to consider: # - Should the Core be able to do geom modifications itself, since it already # has the grid constructed from the grid design? # - Should the summary be so specifically Material data? Should this be done for # non-Cores? Like geom modifications, could this just be done in processLoading? # Should it be invoked higher up, by whatever code is requesting the Reactor be # built from Blueprints? if isinstance(system, reactors.Core): summarizeMaterialData(system) self._modifyGeometry(system, gridDesign) system.processLoading(cs) return system
def test_recursionPin(self): """Ensure pin the center assem has axial coordinates consistent with a pin in an off-center assembly.""" core = MockArmiObject() assem = MockArmiObject(core) block = MockArmiObject(assem) # 2-D grid coreGrid = grids.CartesianGrid.fromRectangle(1.0, 1.0, armiObject=core) # 1-D z-mesh assemblyGrid = grids.Grid(bounds=(None, None, numpy.arange(5)), armiObject=assem) # pins sit in this 2-D grid. blockGrid = grids.CartesianGrid.fromRectangle(0.1, 0.1, armiObject=block) coreLoc = grids.CoordinateLocation(0.0, 0.0, 0.0, None) core.spatialLocator = coreLoc assemblyLoc = grids.IndexLocation(0, 0, 0, coreGrid) assem.spatialLocator = assemblyLoc blockLoc = grids.IndexLocation(0, 0, 3, assemblyGrid) block.spatialLocator = blockLoc pinIndexLoc = grids.IndexLocation(1, 5, 0, blockGrid) assert_allclose(pinIndexLoc.getCompleteIndices(), (1, 5, 0))
def test_locationPackingOldVersion(self): # pylint: disable=protected-access version = 3 loc1 = grids.IndexLocation(1, 2, 3, None) loc2 = grids.CoordinateLocation(4.0, 5.0, 6.0, None) loc3 = grids.MultiIndexLocation(None) loc3.append(grids.IndexLocation(7, 8, 9, None)) loc3.append(grids.IndexLocation(10, 11, 12, None)) locs = [loc1, loc2, loc3] tp, data = database3._packLocations(locs, minorVersion=version) self.assertEqual(tp[0], "I") self.assertEqual(tp[1], "C") self.assertEqual(tp[2], "M:2") unpackedData = database3._unpackLocations(tp, data, minorVersion=version) self.assertEqual(unpackedData[0], (1, 2, 3)) self.assertEqual(unpackedData[1], (4.0, 5.0, 6.0)) self.assertEqual(unpackedData[2][0], (7, 8, 9)) self.assertEqual(unpackedData[2][1], (10, 11, 12))
def __init__(self, name, r=None): composites.Composite.__init__(self, name) self.parent = r # make a Cartesian assembly rack self.spatialGrid = grids.CartesianGrid.fromRectangle(50.0, 50.0) # CoreParameterCollections get CORE by default; we arent ready for that yet here, so turn it # off. self.p.flags = self.p.flags & ~Flags.CORE # random non-zero location to be updated with user-input later self.spatialLocator = grids.CoordinateLocation(100.0, 100.0, 350.0, None)
def test_recursionPin(self): """Ensure pin the center assem has axial coordinates consistent with a pin in an off-center assembly.""" reactorGrid = grids.cartesianGridFromRectangle(1.0, 1.0) # 2-D grid assemblyGrid = grids.Grid(bounds=(None, None, numpy.arange(5))) # 1-D z-mesh blockGrid = grids.cartesianGridFromRectangle( 0.1, 0.1 ) # pins sit in this 2-D grid. reactorLoc = grids.CoordinateLocation(0.0, 0.0, 0.0, None) assemblyLoc = MockLocator(0, 0, 0, reactorGrid) blockLoc = MockLocator(0, 0, 3, assemblyGrid) pinIndexLoc = MockLocator(1, 5, 0, blockGrid) pinIndexLoc._parent = blockLoc blockLoc._parent = assemblyLoc assemblyLoc._parent = reactorLoc assert_allclose(pinIndexLoc.getCompleteIndices(), (1, 5, 0))
def test_locationPacking(self): # pylint: disable=protected-access loc1 = grids.IndexLocation(1, 2, 3, None) loc2 = grids.CoordinateLocation(4.0, 5.0, 6.0, None) loc3 = grids.MultiIndexLocation(None) loc3.append(grids.IndexLocation(7, 8, 9, None)) loc3.append(grids.IndexLocation(10, 11, 12, None)) locs = [loc1, loc2, loc3] tp, data = database3._packLocations(locs) self.assertEqual(tp[0], database3.LOC_INDEX) self.assertEqual(tp[1], database3.LOC_COORD) self.assertEqual(tp[2], database3.LOC_MULTI + "2") unpackedData = database3._unpackLocations(tp, data) self.assertEqual(unpackedData[0], (1, 2, 3)) self.assertEqual(unpackedData[1], (4.0, 5.0, 6.0)) self.assertEqual(unpackedData[2], [(7, 8, 9), (10, 11, 12)])
def test_locationPacking(self): # pylint: disable=protected-access loc1 = grids.IndexLocation(1, 2, 3, None) loc2 = grids.CoordinateLocation(4.0, 5.0, 6.0, None) loc3 = grids.MultiIndexLocation(None) loc3.append(grids.IndexLocation(7, 8, 9, None)) loc3.append(grids.IndexLocation(10, 11, 12, None)) tp, data = database._packLocation(loc1) self.assertEqual(tp, database.LOC_INDEX) unpacked = database._unpackLocation([tp], data) self.assertEqual(unpacked[0], (1, 2, 3)) tp, data = database._packLocation(loc2) self.assertEqual(tp, database.LOC_COORD) unpacked = database._unpackLocation([tp], data) self.assertEqual(unpacked[0], (4.0, 5.0, 6.0)) tp, data = database._packLocation(loc3) self.assertEqual(tp, database.LOC_MULTI + "2") unpacked = database._unpackLocation([tp], data) self.assertEqual(unpacked[0], (7, 8, 9))