Skip to content
Extraits de code Groupes Projets
tmc.py 8,18 ko
Newer Older
  • Learn to ignore specific revisions
  • import numpy as np
    import random as rd
    
    class TransitionMatrixCalculator:
        def __init__(self):
            # Initialisation des matrices de transition pour les dés "safe", "normal" et "risky"
            self.matrix_safe = np.zeros((15, 15))
            self.matrix_normal = np.zeros((15, 15))
            self.matrix_risky = np.zeros((15, 15))
            # Probability to go from state k to k'
    
    Adrien Payen's avatar
    Adrien Payen a validé
            self.safe_dice = np.array([1/2, 1/2])
            self.normal_dice = np.array([1/3, 1/3, 1/3])
            self.risky_dice = np.array([1/4, 1/4, 1/4, 1/4])
    
        
        def compute_transition_matrix(self, layout, circle=False):
            self.matrix_safe.fill(0)
            self.matrix_normal.fill(0)
            self.matrix_risky.fill(0)
    
    
    Adrien Payen's avatar
    Adrien Payen a validé
            self._compute_safe_matrix()
    
            self._compute_normal_matrix(layout, circle)
            self._compute_risky_matrix(layout, circle)
    
            return self.matrix_safe, self.matrix_normal, self.matrix_risky
    
    
    
    Adrien Payen's avatar
    Adrien Payen a validé
        def _compute_safe_matrix(self):
    
    Adrien Payen's avatar
    Adrien Payen a validé
            for k in range(15):
    
                for s, p in enumerate(self.safe_dice):
                    if k == 9 and s == 1:
                        k_prime = 14
                        self.matrix_safe[k,k_prime] += p
                    elif k == 2 and s > 0:
                        p /= 2
                        k_prime = 10
                        self.matrix_safe[k,k_prime] += p
                        k_prime = 3
                        self.matrix_safe[k,k_prime] += p
                    else:
                        k_prime = k + s
                        k_prime = min(14, k_prime)
                        self.matrix_safe[k,k_prime] += p
    
            return self.matrix_safe
    
        def _compute_normal_matrix(self, layout, circle):
    
    Adrien Payen's avatar
    Adrien Payen a validé
            for k in range(15):
    
                for s, p in enumerate(self.normal_dice):
                    if k == 8 and s == 2:
                        k_prime = 14
                        self.matrix_normal[k,k_prime] += p
                        continue
                    elif k == 9 and s in [1, 2]:
                        if not circle or s == 1:
                            k_prime = 14
                            self.matrix_normal[k,k_prime] += p
                        elif circle and s == 2:
                            k_prime = 0
                            self.matrix_normal[k,k_prime] += p
                        continue
    
                    # handle the fast lane
                    if k == 2 and s > 0:
                        p /= 2
    
    Adrien Payen's avatar
    Adrien Payen a validé
                        k_prime = 10 + (s - 1) # rebalance the step before with s > 0
    
                        if layout[k_prime] in [0, 3]:  # normal or prison square
                            self.matrix_normal[k,k_prime] += p
                        elif layout[k_prime] == 1:  # handle type 1 trap
                            self.matrix_normal[k,k_prime] += p / 2
                            k_prime = 0
                            self.matrix_normal[k,k_prime] += p / 2
                        elif layout[k_prime] == 2:  # handle type 2 trap
                            self.matrix_normal[k,k_prime] += p / 2
                            if k_prime == 10:
                                k_prime = 0
                            elif k_prime == 11:
                                k_prime = 1
                            elif k_prime == 12:
                                k_prime = 2
                            else:
                                k_prime = max(0, k_prime - 3)
                            self.matrix_normal[k,k_prime] += p / 2
    
    Adrien Payen's avatar
    Adrien Payen a validé
                        k_prime = 3 + (s - 1) # rebalance the step before with s > 0
    
                        if layout[k_prime] in [0, 3]:  # normal or prison square
                            self.matrix_normal[k,k_prime] += p
                        elif layout[k_prime] == 1:  # handle type 1 trap
                            self.matrix_normal[k,k_prime] += p / 2
                            k_prime = 0
                            self.matrix_normal[k,k_prime] += p / 2
                        elif layout[k_prime] == 2:  # handle type 2 trap
                            self.matrix_normal[k,k_prime] += p / 2
                            k_prime = max(0, k_prime - 3)
                            self.matrix_normal[k,k_prime] += p / 2
                        continue
    
                    k_prime = k + s
    
    Adrien Payen's avatar
    Adrien Payen a validé
                    k_prime = k_prime % 15 if circle else min(14, k_prime) # modulo
    
                    if layout[k_prime] in [1, 2]:
                        p /= 2
                        if layout[k_prime] == 1:
                            k_prime = 0
                            self.matrix_normal[k,k_prime] += p
                            continue
                        elif layout[k_prime] == 2:
                            if k_prime == 10:
                                k_prime = 0
                            elif k_prime == 11:
                                k_prime = 1
                            elif k_prime == 12:
                                k_prime = 2
                            else:
                                k_prime = max(0, k_prime - 3)
                            self.matrix_normal[k,k_prime] += p
                            continue
                    self.matrix_normal[k,k_prime] += p
            return self.matrix_normal
    
        def _compute_risky_matrix(self, layout, circle):
    
    Adrien Payen's avatar
    Adrien Payen a validé
            for k in range(15):
    
                for s, p in enumerate(self.risky_dice):
                    if k == 7 and s == 3:
                        k_prime = 14
                        self.matrix_risky[k,k_prime] += p
                        continue
                    elif k == 8 and s in [2, 3]:
                        if not circle or s == 2:
                            k_prime = 14
                            self.matrix_risky[k,k_prime] += p
                        elif circle:
                            k_prime = 0
                            self.matrix_risky[k,k_prime] += p
                        continue
                    elif k == 9 and s in [1, 2, 3]:
                        if not circle or s == 1:
                            k_prime = 14
                            self.matrix_risky[k,k_prime] += p
                        elif circle and s == 2:
                            k_prime = 0
                            self.matrix_risky[k,k_prime] += p
                        elif circle and s == 3:
                            k_prime = 1
                            if layout[k_prime] != 0:
                                if layout[k_prime] == 1:
                                    k_prime = 0
                                    self.matrix_risky[k,k_prime] += p
                                elif layout[k_prime] == 2:
                                    k_prime = max(0, k_prime - 3)
                                    self.matrix_risky[k,k_prime] += p
                                self.matrix_risky[k,k_prime] += p
                                continue
                        continue
    
                    if k == 2 and s > 0:
                        p /= 2
                        k_prime = 10 + (s - 1)
                        if layout[k_prime] == 1:
                            k_prime = 0
                            self.matrix_risky[k,k_prime] += p
                        elif layout[k_prime] == 2:
                            if k_prime == 10:
                                k_prime = 0
                            elif k_prime == 11:
                                k_prime = 1
                            elif k_prime == 12:
                                k_prime = 2
                            else:
                                k_prime = max(0, k_prime - 3)
                            self.matrix_risky[k,k_prime] += p
                        else:
                            self.matrix_risky[k,k_prime] += p
                        k_prime = 3 + (s - 1)
                        self.matrix_risky[k,k_prime] += p
                        continue
    
                    k_prime = k + s
                    k_prime = k_prime % 15 if circle else min(14, k_prime)
    
    Adrien Payen's avatar
    Adrien Payen a validé
                    if layout[k_prime] in [1, 2]:
    
                        if layout[k_prime] == 1:
                            k_prime = 0
                            self.matrix_risky[k,k_prime] += p
                            continue
                        elif layout[k_prime] == 2:
                            if k_prime == 10:
                                k_prime = 0
                            elif k_prime == 11:
                                k_prime = 1
                            elif k_prime == 12:
                                k_prime = 2
                            else:
                                k_prime = max(0, k_prime - 3)
                            self.matrix_risky[k,k_prime] += p
                            continue
                    self.matrix_risky[k,k_prime] += p
            return self.matrix_risky
    
    #tmc = TransitionMatrixCalculator()
    #tmc.tst_transition_matrix()