2015-05-12 34 views
2

什麼是創建一個類型,它是在Python飽和整數的最佳方法?在python中創建一個飽和整數的最佳方法?

即:

v = SaturatedInteger(0, 100) 
# That should create an integer that will always be in between 0 and 100, 
# and have all default operations 

v += 68719 
print v #Should print '100'. 

我能想到的繼承int型的,但應該在哪裏飽合邏輯來實現呢?

+1

查看https://docs.python.org/2/reference/datamodel.html#emulating-numeric-types – jonrsharpe

+0

我只是好奇而已:像夾具一樣飽和(我在OpenGL中看到的一個術語)? –

+0

@DavidEhrmann夾緊是當範圍是通過一個單獨的步驟固定用的術語,而飽和是在操作本身期間施加限制。兩者的結果應該完全相同。 –

回答

3

如果你需要一個新的(快速和骯髒的)班,我會實現它作爲如下。

class SaturatedInteger: 
    def __init__(self, val, lo, hi): 
     self.real, self.lo, self.hi = val, lo, hi 

    def __add__(self, other): 
     return min(self.real + other.real, self.hi) 

    def __sub__(self, other): 
     return max(self.real - other.real, self.lo) 

    ... 

你覺得你需要(和他們的「r」變種)添加爲許多其他運營商的the docs

通過實例名稱real存儲的值,你可以用普通的整數做你的算術,花車等太:

a = SaturatedInteger(60, 0, 100) 
print(a) 
60 
print(a+30) 
90 
print(a+40) 
100 
print(a+50.) 
100 
print(a-70.) 
0 
print(a+a) 
100 

雖然,你當然只有當你添加的實部給你的SaturatedInteger增加一個複數,所以要小心。 (對於一個更加完整和強大的版本,@ jonrsharpe的答案是要走的路)。

+0

了'.real'是一個很好的方法,它增加互操作性使用應該實現'__add__'。 –

0

我寫了一個具有附加功能的示例類:

class SatInt: 
    def __init__(self, low, up): 
     self.lower = low 
     self.upper = up 
     self.value = 0 

    def add(self, n): 
     if n+self.value > self.upper: 
      self.value = self.upper 
     else: 
      self.value = self.value + n 


x = SatInt(0,100) 
x.add(32718) 
print(x.value) 
+1

而不是'add',你這樣它可以用'+'... – jonrsharpe

1

在一般情況下,我將實現使用@property保護實例的value屬性,然後emulate a numeric type,而不是從int繼承:

class SaturatedInteger(object): 
    """Emulates an integer, but with a built-in minimum and maximum.""" 

    def __init__(self, min_, max_, value=None): 
     self.min = min_ 
     self.max = max_ 
     self.value = min_ if value is None else value 

    @property 
    def value(self): 
     return self._value 

    @value.setter 
    def value(self, new_val): 
     self._value = min(self.max, max(self.min, new_val)) 

    @staticmethod 
    def _other_val(other): 
     """Get the value from the other object.""" 
     if hasattr(other, 'value'): 
      return other.value 
     return other 

    def __add__(self, other): 
     new_val = self.value + self._other_val(other) 
     return SaturatedInteger(self.min, self.max, new_val) 

    __radd__ = __add__ 

    def __eq__(self, other): 
     return self.value == self._other_val(other) 


if __name__ == '__main__': 
    v = SaturatedInteger(0, 100) 
    v += 68719 
    assert v == 100 
    assert 123 + v == 100 

我只實現__add____radd____eq__,但你可以可能會看到其餘部分可以如何根據需要構建出來。您可能想要考慮兩個SaturatedInteger一起使用時會發生什麼 - 如果結果是例如min(self.min, other.min)作爲自己的min

+0

這是一個很好的答案,並在最後一個非常有趣的問題:)謝謝。 –

相關問題