Beispiel #1
0
    def __init__(self):
        super().__init__()  # llama a la creación de AerModel
        print('- Inicializando Transitorio')
        self._C0 = {}
        self.__Ct_1 = {}
        self._Ct = {}
        self.__FILENAME = 'aer.cii'
        self.__ROOTFILE = self.__FILENAME[:-4]
        self.__DATABASE = self.__ROOTFILE + '_eq.cdb'
        self.__Geom = Geometry(self.__FILENAME.replace('.cii', '_geo.ci@'))
        self.__NuFis = NuFissionMap()
        self.__KM = KineticMap()
        self._NOG = 2  # TODO: Sería mejor extraer del ci@?
        self.chi_g = [1.0, 0.0]  # TODO: Sería mejor extraer del ci@?
        self.__Flux_t_1 = self.Flux = MeshFlux(
            self.__DATABASE + '.meshflux', *self.__Geom.Cantidad_de_Nodos(),
            self._NOG)
        Nx, Ny, Nz, _NOG = self.Flux.shape[1:]
        self.BetaM = np.empty((1, Nx, Ny, Nz, 6))
        self.LambdaM = np.empty((1, Nx, Ny, Nz, 6))
        self.NuFisM = np.empty((1, Nx, Ny, Nz, _NOG))
        self.VelocityM = np.empty((1, Nx, Ny, Nz, _NOG))
        state = 0
        static_react = -123.1  # reactividad inicial inicial, no inicial
        self.keff = 1 / (1 - static_react / 100000)
        self._Q = {}
        self.EQUILIBRIUM = True
        self.powers = []

        for _x in range(Nx):
            for _y in range(Ny):
                for _z in range(Nz):
                    meshmaterial = self.__Geom.sc5[_x][_y][_z]

                    kwargs = {'list_fuels': self.list_fuels, 'time': 0}
                    self.BetaM[state][_x][_y][_z][:] = \
                        self.__KM.MapMaterial(meshmaterial, **kwargs)['Beta']
                    self.LambdaM[state][_x][_y][_z][:] = \
                        self.__KM.MapMaterial(meshmaterial, **kwargs)['Decays']
                    self.VelocityM[state][_x][_y][_z][:] = \
                        self.__KM.MapMaterial(meshmaterial, **kwargs)['Neutron Velocity']
                    self.NuFisM[state][_x][_y][_z][:] = \
                        self.__NuFis.MapMaterial(meshmaterial, **kwargs)['XS'][:, 3] / self.keff
Beispiel #2
0
        if args:
            return self._FISS[DEFAULT_STATE][DEFAULT_BURNUP][args[0]].shape[0]
        return self._FISS[DEFAULT_STATE][DEFAULT_BURNUP]['Decays'].shape[0]


if __name__ == '__main__':

    from citvappru.SourceCAREM2_1_1 import Geometry, PrecCalc
    import re

    os.chdir('C:\\CUBEM\\')
    FILENAME = 'cube.cii'
    ROOTFILE = FILENAME[:-4]
    DATABASE = ROOTFILE + '_eq.cdb'

    Geom = Geometry(FILENAME.replace('.cii', '0.cii'))

    NuFis = Nu_Fission_Map()
    KM = Kinetic_Map(NPRC=1)

    _NOG = 1

    NPRC = KM.get_NPRC()

    Flux = MeshFlux(DATABASE + '.meshflux', *Geom.Cantidad_de_Nodos(), _NOG)
    Nx, Ny, Nz = Flux.shape[1:4]

    BetaM = np.empty((1, Nx, Ny, Nz, NPRC))
    LambdaM = np.empty((1, Nx, Ny, Nz, NPRC))
    NuFisM = np.empty((1, Nx, Ny, Nz, _NOG))
    VelocityM = np.empty((1, Nx, Ny, Nz, _NOG))
Beispiel #3
0
def mainnomain():
    os.chdir('D:\\AER\\')
    FILENAME = 'aer.cii'
    ROOTFILE = FILENAME[:-4]
    DATABASE = ROOTFILE + '_eq.cdb'

    Geom = Geometry(FILENAME.replace('.cii', '_geo.ci@'))
    NuFis = NuFissionMap()
    KM = KineticMap()
    _NOG = 2
    Flux = MeshFlux(DATABASE + '.meshflux', *Geom.Cantidad_de_Nodos(), _NOG)
    Nx, Ny, Nz = Flux.shape[1:4]

    BetaM = np.empty((1, Nx, Ny, Nz, 1))
    LambdaM = np.empty((1, Nx, Ny, Nz, 1))
    NuFisM = np.empty((1, Nx, Ny, Nz, _NOG))
    VelocityM = np.empty((1, Nx, Ny, Nz, _NOG))

    state = 0

    Vmesh = Geom.Vmesh()

    react = -123.1  # reactividad inicial inicial, no inicial
    keff = 1 / (1 - react / 100000)

    for _x in range(Nx):
        for _y in range(Ny):
            for _z in range(Nz):
                meshmaterial = Geom.sc5[_x][_y][_z]

                KinParam = KM.MapMaterial(meshmaterial)  # Obsoleto

                BetaM[state][_x][_y][_z][:] = KinParam['Beta']

                LambdaM[state][_x][_y][_z][:] = KinParam['Decays']

                VelocityM[state][_x][_y][_z][:] = KinParam['Neutron Velocity']

                NuFisM[state][_x][_y][_z][:] = NuFis.MapMaterial(
                    meshmaterial)['XS'][:, 3] / keff

    C0 = {}
    NPRC = BetaM.shape[-1]
    C0[state] = {}
    for nx in range(Flux.shape[1]):
        C0[state][nx] = {}
        for ny in range(Flux.shape[2]):
            C0[state][nx][ny] = {}
            for nz in range(Flux.shape[3]):
                FluxL = [
                    Flux[state, nx, ny, nz, group]
                    for group in range(Flux.shape[-1])
                ]
                NuFisL = [
                    NuFisM[state][nx][ny][nz][group]
                    for group in range(Flux.shape[-1])
                ]
                Nu_FluxM = [
                    NuFisL[group] * FluxL[group] * Vmesh
                    for group in range(Flux.shape[-1])
                ]

                Bet_k = BetaM[state][nx][ny][nz]
                Lamb_k = LambdaM[state][nx][ny][nz]
                Nu_Flux = sum(Nu_FluxM)

                C0[state][nx][ny][nz] = [
                    Bet_k[prec] * Nu_Flux /
                    Lamb_k[prec] if Lamb_k[prec] != 0 else 0.0
                    for prec in range(NPRC)
                ]

    p = re.compile(r'POWER\(WATTS\)\s+([0-9]\.[0-9]{5}E\+[0-9]{2})')
    powers = []

    Q = {}
    EQUILIBRIUM = True
    chi_g = [1.0, 0.0]

    v1 = 1.25E+7
    v2 = 2.50E+5
    dt = 0.01
    tfinal = 0.5
    DATABASE = ROOTFILE + 'S.cdb'
    Times = np.arange(0, tfinal + 2 * dt, dt)
    FAILED_COMPLETE_TEST = False
    DERIVATIVE = True
    for t in Times:
        if EQUILIBRIUM:
            C_t_1 = C0.copy()
            C_t = C0.copy()
            Flux_t_1 = Flux
        else:
            TFlux = MeshFlux(DATABASE + '.meshflux', Nx, Ny, Nz, _NOG)
            # noinspection PyUnboundLocalVariable
            C_t = PrecCalc(C_t_1,
                           TFlux,
                           NuFisM,
                           Vmesh,
                           dt,
                           LambdaM=LambdaM,
                           BetaM=BetaM)

            C_t_1 = C_t.copy()
            Flux_t_1 = TFlux

        for group in range(Flux.shape[-1]):
            Q[group] = {}
            for state in range(Flux.shape[0]):
                Q[group][state] = {}
                for nx in range(Flux.shape[1]):
                    Q[group][state][nx] = {}
                    for ny in range(Flux.shape[2]):
                        Q[group][state][nx][ny] = {}
                        for nz in range(Flux.shape[3]):
                            _Lmk = LambdaM[state][nx][ny][nz]
                            _C = C_t[state][nx][ny][nz]

                            _invV = VelocityM[state, nx, ny, nz, group]
                            T_1Flux = Flux_t_1[state, nx, ny, nz, group]

                            Q[group][state][nx][ny][nz] = \
                                chi_g[group] * sum([_Lmk[prc] * _C[prc] for prc in range(NPRC)]) \
                                + _invV / dt * T_1Flux * Vmesh * DERIVATIVE  #

        with open('source.dat', 'w') as fod:
            for group in range(_NOG):
                for state in range(Flux.shape[0]):
                    for nz in range(Flux.shape[3]):
                        for ny in range(Flux.shape[2]):
                            for nx in range(Flux.shape[1]):
                                fod.write('{:15.7E}'.format(
                                    Q[group][state][nx][ny][nz]))
                fod.write('\n')
        # Ejecución de archivo AQUI
        OsArgs = (FILENAME.replace('.cii',
                                   'S.cii'), _NOG, Nx, Ny, Nz, EQUILIBRIUM,
                  *['{:12.5E}'.format(_d) for _d in [dt * DERIVATIVE, t]])
        # PARA HACER UNA PERTURBACION ESCALOR,COLOCAR t=1
        # PARA CALCULAR SIN DERIVADA TEMPORAL dt=0
        try:
            os.system('ExAer.bat ' + ' '.join(map(str, OsArgs)))
            fid = open(ROOTFILE + 'S.cio', 'r')
            powers.append(float(next(p.finditer(fid.read())).groups()[0]))
            print(powers[-1])
            fid.close()
            if EQUILIBRIUM: EQUILIBRIUM = False
        except StopIteration:
            FAILED_COMPLETE_TEST = True
            break
            pass

    Normalized_Pow = np.array(powers) / 1E+06
    if FAILED_COMPLETE_TEST: Times = [k * dt for k in range(len(powers))]
    return
Beispiel #4
0
class AerEvolution(AerModel):
    def __init__(self):
        super().__init__()  # llama a la creación de AerModel
        print('- Inicializando Transitorio')
        self._C0 = {}
        self.__Ct_1 = {}
        self._Ct = {}
        self.__FILENAME = 'aer.cii'
        self.__ROOTFILE = self.__FILENAME[:-4]
        self.__DATABASE = self.__ROOTFILE + '_eq.cdb'
        self.__Geom = Geometry(self.__FILENAME.replace('.cii', '_geo.ci@'))
        self.__NuFis = NuFissionMap()
        self.__KM = KineticMap()
        self._NOG = 2  # TODO: Sería mejor extraer del ci@?
        self.chi_g = [1.0, 0.0]  # TODO: Sería mejor extraer del ci@?
        self.__Flux_t_1 = self.Flux = MeshFlux(
            self.__DATABASE + '.meshflux', *self.__Geom.Cantidad_de_Nodos(),
            self._NOG)
        Nx, Ny, Nz, _NOG = self.Flux.shape[1:]
        self.BetaM = np.empty((1, Nx, Ny, Nz, 6))
        self.LambdaM = np.empty((1, Nx, Ny, Nz, 6))
        self.NuFisM = np.empty((1, Nx, Ny, Nz, _NOG))
        self.VelocityM = np.empty((1, Nx, Ny, Nz, _NOG))
        state = 0
        static_react = -123.1  # reactividad inicial inicial, no inicial
        self.keff = 1 / (1 - static_react / 100000)
        self._Q = {}
        self.EQUILIBRIUM = True
        self.powers = []

        for _x in range(Nx):
            for _y in range(Ny):
                for _z in range(Nz):
                    meshmaterial = self.__Geom.sc5[_x][_y][_z]

                    kwargs = {'list_fuels': self.list_fuels, 'time': 0}
                    self.BetaM[state][_x][_y][_z][:] = \
                        self.__KM.MapMaterial(meshmaterial, **kwargs)['Beta']
                    self.LambdaM[state][_x][_y][_z][:] = \
                        self.__KM.MapMaterial(meshmaterial, **kwargs)['Decays']
                    self.VelocityM[state][_x][_y][_z][:] = \
                        self.__KM.MapMaterial(meshmaterial, **kwargs)['Neutron Velocity']
                    self.NuFisM[state][_x][_y][_z][:] = \
                        self.__NuFis.MapMaterial(meshmaterial, **kwargs)['XS'][:, 3] / self.keff

    @property
    def Ct_1(self):
        """
        Precursores calculados en el paso anterior
        """
        return self.__Ct_1.copy()

    @property
    def Ct(self):
        """
        Precursores calculados hasta ahora.
        """
        return AddableDict(self._Ct)

    @property
    def C0(self):
        """
        Precursores de Equilibrio (reactor estático)
        """
        return AddableDict(self._C0)

    def equilibrium_precrs(self):
        print('- Calculando precursores en equilibrio')
        state = 0
        Vmesh = self.__Geom.Vmesh()

        NPRC = self.BetaM.shape[-1]
        self._C0[state] = {}
        for nx in range(self.Flux.shape[1]):
            self._C0[state][nx] = {}
            for ny in range(self.Flux.shape[2]):
                self._C0[state][nx][ny] = {}
                for nz in range(self.Flux.shape[3]):
                    FluxL = [
                        self.Flux[state, nx, ny, nz, group]
                        for group in range(self.Flux.shape[-1])
                    ]
                    NuFisL = [
                        self.NuFisM[state][nx][ny][nz][group]
                        for group in range(self.Flux.shape[-1])
                    ]
                    Nu_FluxM = [
                        NuFisL[group] * FluxL[group] * Vmesh
                        for group in range(self.Flux.shape[-1])
                    ]

                    Bet_k = self.BetaM[state][nx][ny][nz]
                    Lamb_k = self.LambdaM[state][nx][ny][nz]
                    Nu_Flux = sum(Nu_FluxM)

                    self._C0[state][nx][ny][nz] = [
                        Bet_k[prec] * Nu_Flux /
                        Lamb_k[prec] if Lamb_k[prec] != 0 else 0.0
                        for prec in range(NPRC)
                    ]
        self.__Ct_1 = self._C0.copy()
        self._Ct = self._C0.copy()

    def calculate_precrs(self, dt):
        TFlux = MeshFlux(self.__DATABASE + '.meshflux',
                         *self.__Geom.Cantidad_de_Nodos()[1:4])
        self._Ct = PrecCalc(self.__Ct_1,
                            TFlux,
                            self.NuFisM,
                            self.__Geom.Vmesh(),
                            dt,
                            LambdaM=self.LambdaM,
                            BetaM=self.BetaM)

        self.__Ct_1 = self._Ct.copy()
        self.__Flux_t_1 = TFlux
        return

    @property
    def Q_as_array(self):
        """
        Fuente calculada al instante t como array de numpy
        """
        return AddableDict(self._Q).as_array()

    def calculate_source(self, **kwargs):
        print('- Calculando la fuente')
        DERIVATIVE = kwargs['DERIVATIVE']
        if DERIVATIVE:
            dt = kwargs['dt']
        else:
            dt = 1
        Vmesh = self.__Geom.Vmesh()
        NPRC = 6
        for group in range(self.Flux.shape[-1]):
            self._Q[group] = {}
            for state in range(self.Flux.shape[0]):
                self._Q[group][state] = {}
                for nx in range(self.Flux.shape[1]):
                    self._Q[group][state][nx] = {}
                    for ny in range(self.Flux.shape[2]):
                        self._Q[group][state][nx][ny] = {}
                        for nz in range(self.Flux.shape[3]):
                            _Lmk = self.LambdaM[state][nx][ny][nz]
                            _C = self._Ct[state][nx][ny][nz]

                            _invV = self.VelocityM[state, nx, ny, nz, group]
                            T_1Flux = self.__Flux_t_1[state, nx, ny, nz, group]

                            self._Q[group][state][nx][ny][nz] = \
                                self.chi_g[group] * sum([_Lmk[prc] * _C[prc] for prc in range(NPRC)]) \
                                + (_invV / dt * T_1Flux * Vmesh if DERIVATIVE else 0)

    def move_control_rods(self, **kwargs):
        Threshold = 1.0
        assert 'time' in kwargs, 'No se ha establecido el tiempo de cálculo'
        Time = kwargs['time']
        Extraction_Velocity = 200 / 0.08
        Extraction_CR_26 = 8 - (Extraction_Velocity *
                                Time) // 25 if Time <= 0.08 else 0
        self.InsertControlRod(Extraction_CR_26, 26)

        if Time > Threshold:
            Insertion_Velocity = 250 / 10.0  # Hasta el fondo del nucleo en 10 segundos
            Insertion_CR_21 = 8 + (Insertion_Velocity *
                                   Time) // 25 if Time <= 2.0 else 10
            Insertion_CR_SS = (Insertion_Velocity *
                               Time) // 25 if Time <= 11.0 else 10
            # Control Rod Secutiry System (23,25)
            self.SCRAM(Insertion_CR_SS)
            self.InsertControlRod(Insertion_CR_21, 21)
            # TODO testear este método y llevarlo a archivo
        return

    def source_to_file(self):
        print('- Escribiendo el Archivo source.dat')
        _NOG = 2
        with open('source.dat', 'w') as fod:
            for group in range(_NOG):
                for state in range(self.Flux.shape[0]):
                    for nz in range(self.Flux.shape[3]):
                        for ny in range(self.Flux.shape[2]):
                            for nx in range(self.Flux.shape[1]):
                                fod.write('{:15.7E}'.format(
                                    self._Q[group][state][nx][ny][nz]))
                            fod.write('\n')
                fod.write('\n')

    def Execute(self, **kwargs):
        self.EQUILIBRIUM = False
        print('- Ejecuntando CITVAP')
        DERIVATIVE = kwargs['DERIVATIVE']
        if DERIVATIVE:
            dt = kwargs['dt']
        else:
            dt = 1
        time = kwargs['time']
        p = re.compile(r'POWER\(WATTS\)\s+([0-9]\.[0-9]{5}E\+[0-9]{2})')
        Nx, Ny, Nz = self.__Geom.Cantidad_de_Nodos()
        OsArgs = (self.__FILENAME.replace('.cii', 'S.cii'), self._NOG, Nx, Ny,
                  Nz, self.EQUILIBRIUM,
                  *['{:12.5E}'.format(_d) for _d in [dt * DERIVATIVE, time]])
        # PARA HACER UNA PERTURBACION ESCALOR,COLOCAR t=1
        # PARA CALCULAR SIN DERIVADA TEMPORAL dt=0
        try:
            os.system('ExEqAer.bat ' + ' '.join(map(str, OsArgs)))
            fid = open(self.__ROOTFILE + 'S.cio', 'r')
            self.powers.append(float(next(p.finditer(fid.read())).groups()[0]))
            print(self.powers[-1])
            fid.close()
            if self.EQUILIBRIUM: self.EQUILIBRIUM = False
        except StopIteration:
            FAILED_COMPLETE_TEST = True
            pass

    # TODO: traer el script a python para ser ejecutado con subprocess.Popen
    pass  # AerEvolution
Beispiel #5
0
    elements = [hexag.type[0] for hexag in
                list(filter(lambda column: 26 in map(lambda hexag: hexag.type[1], column), alf.grid))[0] if
                hexag.type[1] not in [5, 1999]]
    pows = PowDens('aer.cdb.powerdensities')
    plt.plot(pows[0, min(elements) - 1:max(elements) - 1, :], '-o')

    Pows = OrderedDict({ file.strip('.pow') : np.genfromtxt(file) for file in glob('INFO\\*.pow')})

    Nods = OrderedDict({file.strip('.nod'): np.genfromtxt(file, comments='*') for file in glob('INFO\\*.nod')})
    Nods = OrderedDict({ key:value.reshape(value.shape[0]//2210,2210,value.shape[1]) for key,value in Nods.items()})

    plt.plot(*reduce(add,[(Pow[:,0],Pow[:,1],'-o') for Pow in Pows.values()]))
    plt.legend(Pows.keys())

    file = 'INFO\\solaeki.reac'
    alf = np.loadtxt(file)
    plt.plot(alf[:, 0], alf[:, 1], 'o')
    return


if __name__ == '__main__':
    # alf = GroupFlux('aer.cdb.flux')
    # plt.plot(range(10),alf[0,0,:,1],'-o',range(10),alf[0,0,:,0],'o-')

    Geo = Geometry('aer_geo.ci@')
    import re
    alfred = re.compile(r'(?<=\s{2}3\n)(?:[\s0-9]{3}){4}([\s0-9]{3})')
    findings = alfred.search(open('aer_geo.ci@').read())
    pass

Beispiel #6
0
 def _init_mesh_parameters(self):
     self.Geom = Geometry(self.__file.replace(
         'S.cii', '0.cii'))  # HARDCODEADO el *S.cii
     self.Vmesh = self.Geom.Vmesh()
     self.Nx, self.Ny, self.Nz = self.Geom.Cantidad_de_Nodos()
     return
Beispiel #7
0
class CubeModel(EvInterface):
    @property
    def Ct_1(self):
        return AddableDict(self._Ct_1).as_array()

    @property
    def C0(self):
        return AddableDict(self._C0).as_array()

    @property
    def Ct(self):
        return AddableDict(self._Ct).as_array()

    @property
    def Q(self):
        return AddableDict(self._Q).as_array()

    def __init__(self,
                 state=0,
                 nprc=1,
                 Equilibrium=True,
                 file='cubeS.cii',
                 UseDerivative=False):

        self.t = 0.0
        self.dt = 0.0
        self.state = state
        self.chi_g = [1.0]
        self.__file = file
        self.Equilibrium = Equilibrium
        self.nprc = nprc

        self.__rootfile = self.__file.replace('.cii', '')
        self.__database = self.__file.replace('.cii', '.cdb')
        self.__p_parser = re.compile(
            r'POWER\(WATTS\) +([0-9]\.[0-9]{5}E\+[0-9]{2})')
        self.Pt = 100
        self._Q = {}

        self._C0 = self._Ct = self._Ct_1 = {self.state: {}}

        self.__UseDerivative = UseDerivative
        self.__datfile = r'source.dat'

        self._init_citvap_model()
        self._init_mesh_parameters()
        self._init_parameters()
        self._init_flux()
        return

    def _init_citvap_model(self):
        self._CV = CitvapSourceModel(file=self.__file,
                                     sec4='cube.sc4',
                                     sec5='cube.sc5',
                                     mat='cube.mat',
                                     sec26='cube.sc26',
                                     GeometricType='XYZ')

        self._CV.PrintMeshMap()
        self._CV.Calculate()
        return

    def _init_flux(self):
        self.Flux_t = self.Flux_t_1 = \
            MeshFlux(self.__database.replace('S.cdb', '_eq.cdb.meshflux')
                                               , self.Nx, self.Ny, self.Nz, self._NOG)
        return

    def _init_parameters(self):
        self.NuFis = Nu_Fission_Map()
        self.KM = Kinetic_Map(NPRC=self.nprc)
        self._NOG = 1
        self.BetaM = np.empty((1, self.Nx, self.Ny, self.Nz, self.nprc))
        self.LambdaM = np.empty((1, self.Nx, self.Ny, self.Nz, self.nprc))
        self.NuFisM = np.empty((1, self.Nx, self.Ny, self.Nz, self._NOG))
        self.VelocityM = np.empty((1, self.Nx, self.Ny, self.Nz, self._NOG))

        for _x in range(self.Nx):
            for _y in range(self.Ny):
                for _z in range(self.Nz):
                    meshmaterial = self.Geom.sc5[_x][_y][_z]
                    KinParam = self.KM.MapMaterial(meshmaterial,
                                                   NPRC=self.nprc)
                    self.BetaM[self.state][_x][_y][_z][:] = KinParam['Beta']
                    self.LambdaM[
                        self.state][_x][_y][_z][:] = KinParam['Decays']
                    self.VelocityM[self.state][_x][_y][_z][:] = KinParam[
                        'Neutron Velocity']
                    self.NuFisM[self.state][_x][_y][
                        _z][:] = self.NuFis.MapMaterial(meshmaterial)['XS'][:,
                                                                            3]

        self.react = self.__R0 = 173.0E-5
        self.keff = 1 / (1 - self.__R0)
        return 0

    def _init_mesh_parameters(self):
        self.Geom = Geometry(self.__file.replace(
            'S.cii', '0.cii'))  # HARDCODEADO el *S.cii
        self.Vmesh = self.Geom.Vmesh()
        self.Nx, self.Ny, self.Nz = self.Geom.Cantidad_de_Nodos()
        return

    def equilibrium_precrs(self, *args, **kwargs):
        if not self._C0[self.state]:
            for nx in range(self.Flux_t.shape[1]):
                self._C0[self.state][nx] = {}
                for ny in range(self.Flux_t.shape[2]):
                    self._C0[self.state][nx][ny] = {}
                    for nz in range(self.Flux_t.shape[3]):
                        FluxL = [
                            self.Flux_t[self.state, nx, ny, nz, group]
                            for group in range(self.Flux_t.shape[-1])
                        ]
                        NuFisL = [
                            self.NuFisM[self.state][nx][ny][nz][group] /
                            self.keff for group in range(self.Flux_t.shape[-1])
                        ]
                        Nu_FluxM = [
                            NuFisL[group] * FluxL[group] * self.Geom.Vmesh()
                            for group in range(self.Flux_t.shape[-1])
                        ]
                        Bet_k = self.BetaM[self.state][nx][ny][nz]
                        Lamb_k = self.LambdaM[self.state][nx][ny][nz]

                        self._C0[self.state][nx][ny][nz] = [
                            Bet_k[prec] / Lamb_k[prec] *
                            sum(Nu_FluxM) if Lamb_k[prec] != 0 else 0.0
                            for prec in range(self.nprc)
                        ]
        return

    def calculate_precrs(self, dt):
        for nx in range(self.Nx):
            # self._Ct[self.state][nx] = {}
            for ny in range(self.Ny):
                # self._Ct[self.state][nx][ny] = {}
                for nz in range(self.Nz):
                    FluxL = [
                        self.Flux_t[self.state, nx, ny, nz, group]
                        for group in range(self._NOG)
                    ]
                    NuFisL = [
                        self.NuFisM[self.state][nx][ny][nz][group]
                        for group in range(self._NOG)
                    ]

                    Bet_k = self.BetaM[self.state][nx][ny][nz]
                    Lamb_k = self.LambdaM[self.state][nx][ny][nz]
                    _c_t_1 = self._Ct_1[self.state][nx][ny][nz]

                    Nu_Flux = [
                        NuFisL[group] * FluxL[group] * self.Geom.Vmesh()
                        for group in range(self._NOG)
                    ]

                    self._Ct[self.state][nx][ny][nz] = \
                        [_c_t_1[prec] * np.exp(-Lamb_k[prec] * dt) +
                         Bet_k[prec] / Lamb_k[prec] * sum(Nu_Flux) * (1 - np.exp(-Lamb_k[prec] * dt))
                         if Lamb_k[prec] != 0 else 0.0 for prec in range(self.nprc)]
        return

    def evolve(self, dt, *args, **kwargs):
        if self.Equilibrium:
            self.equilibrium_precrs()
            self._Ct = self._C0.copy()
            self._Ct_1 = self._C0.copy()
        else:
            self._Ct_1 = self._Ct.copy()
            self.calculate_precrs(dt)
            self.t += dt

        if self.__UseDerivative:
            self.dt = dt

        self.calculate_source(dt)
        self.source_to_file()
        self.__send_to_lu_17__()
        self.__xsu_mod__()
        self.run()
        self.__get_power__()

        if self.Equilibrium:
            self.Equilibrium = False

        self.Flux_t_1 = self.Flux_t.copy()
        self.Flux_t = MeshFlux(self.__database + '.meshflux', self.Nx, self.Ny,
                               self.Nz, self._NOG)
        return

    def source_to_file(self):
        with open(self.__datfile, 'w') as fod:
            for group in range(self._NOG):
                for nz in range(self.Nz):
                    for ny in range(self.Ny):
                        for nx in range(self.Nx):
                            fod.write('{:15.7E}'.format(
                                self._Q[group][self.state][nx][ny][nz]))
                fod.write('\n')
        return

    def __send_to_lu_17__(self):
        subprocess.run(['copy', '/Y', self.__datfile, 'Source_To_LU17'],
                       shell=True)
        os.chdir('C:\\CUBEM\\Source_To_LU17')
        msg = subprocess.run(
            ['main.exe', *map(str, [self._NOG, self.Nx, self.Ny, self.Nz])],
            shell=True,
            capture_output=True)
        msg2 = subprocess.run(
            ['copy', '/Y', 'fort.17', '..\\' + self.__rootfile + '.src'],
            shell=True,
            capture_output=True)
        os.chdir('C:\\CUBEM')
        return msg

    def __xsu_mod__(self):
        XSU_FILE = '{}'.format(self.__rootfile + '.XSU')
        try:
            self._CV.run(executable='pre_cit.exe')
        except AssertionError:
            time.sleep(2.0)
            self._CV.run(executable='pre_cit.exe')

        subprocess.run(['move', XSU_FILE, 'XSU_MOD\\'], shell=True)
        os.chdir('C:\\CUBEM\\XSU_MOD')
        if self.__UseDerivative:
            time_step = self.dt
        else:
            time_step = 0.0
        msg = subprocess.run([
            'neutyp', '{}'.format(XSU_FILE),
            str(self.Equilibrium),
            *map(lambda a: '{:12.5E}'.format(round(a, ndigits=5)),
                 [time_step, self.t])
        ],
                             shell=True,
                             capture_output=True)
        assert msg.stderr in [
            '', b''
        ], 'Error en la sobreescritura del archivo ROOT.XSU'
        os.chdir('C:\\CUBEM')
        msg2 = subprocess.run([
            'move', '/Y', 'C:\\CUBEM\\XSU_MOD\\{}'.format(XSU_FILE), XSU_FILE
        ],
                              shell=True,
                              capture_output=True)
        assert msg2.stderr in ['', b''
                               ], 'Error en el movimiento del archivo ROOT.XSU'
        return msg

    def __get_power__(self, file=None):
        if not file:
            fid = open(self.__rootfile + '.cio', 'r')
        else:
            fid = open(file, 'r')
        self.Pt = float(self.__p_parser.findall(fid.read())[0])
        fid.close()
        return

    def run(self):
        try:
            self._CV.run(executable='cittrs.exe')
        except AssertionError:
            time.sleep(2.0)
            self._CV.run(executable='cittrs.exe')
        subprocess.run(
            ['caremdb', '-opt:export', '-val:meshflux', self.__database])
        return

    def calculate_source(self, dt):
        for group in range(self.Flux_t.shape[-1]):
            self._Q[group] = {self.state: {}}
            for nx in range(self.Flux_t.shape[1]):
                self._Q[group][self.state][nx] = {}
                for ny in range(self.Flux_t.shape[2]):
                    self._Q[group][self.state][nx][ny] = {}
                    for nz in range(self.Flux_t.shape[3]):
                        _Lmk = self.LambdaM[self.state][nx][ny][nz]
                        _C = self._Ct[self.state][nx][ny][nz]

                        inv_V = self.VelocityM[self.state, nx, ny, nz, group]

                        self._Q[group][self.state][nx][ny][nz] = \
                            self.chi_g[group] * sum([_Lmk[prc] * _C[prc] for prc in range(self.nprc)])
                        if self.__UseDerivative:
                            self._Q[group][self.state][nx][ny][nz] +=\
                                inv_V / dt * self.Flux_t_1[self.state, nx, ny, nz, group] * self.Vmesh
        return

    pass  # CubeModel