[PYTHON] Sortieren Sie zufällige FizzBuzz-Spalten mit schneller Sortierung

Einführung

Ich habe letztes Mal schnelles Sortieren gelernt. Die Sorge war, was zu tun ist, weil es viele große und kleine Vergleiche gibt. http://qiita.com/cof/items/7b94aac6794d12ae020f

Lösung

  1. Erstellen Sie eine Klasse, die FizzBuzz einem numerischen Wert zuordnet, und überladen Sie den Operator in dieser Klasse.
  2. Ersetzen Sie die Elemente der Zufallsspalte durch eine Instanz der obigen Klasse.
  3. Sortieren Sie die ersetzten zufälligen Spalten schnell.

Es ist schneller, es einmal vollständig zu digitalisieren, schnell zu sortieren und später durch FizzBuzz zu ersetzen. Als Übung zum Überladen von Operatoren habe ich eine Klasse erstellt, die FizzBuzz mit Zahlen verknüpft. Referenz: http://docs.python.jp/2/reference/datamodel.html#customization

Überlastung des Bedieners

Ein Code, der eine Operation für den Wert ausführt, der einer Zeichenfolge usw. (Schlüssel) zugeordnet ist, und die Zeichenfolge usw. zurückgibt, die dem resultierenden Schlüssel entspricht.

def fizzbuzz(n):
  if (n%15) == 0: return 'FizzBuzz'
  elif (n%5) == 0: return 'Buzz'
  elif (n%3) == 0: return 'Fizz'
  else: return n

class FizzBuzzNumber:
  def __init__(self, value):
    self.key = fizzbuzz(value)
    self.value = value

  def __call__(self):
    return self.key

  def __add__(self, other) :
    return fizzbuzz(self.value + other.value)

  def __sub__(self, other):
    return fizzbuzz(self.value - other.value)

  def __mul__(self, other):
    return fizzbuzz(self.value * other.value)

  def __div__(self, other):
    return fizzbuzz(self.value // other.value)

  def __mod__(self, other):
    return fizzbuzz(self.value % other.value)

  def __pow__(self, other):
    return fizzbuzz(self.value ** other.value)

  def __cmp__(self, other):
    return cmp(self.value, other.value)

  def __lt__(self, other):
    return cmp(self.value, other.value) == -1

  def __le__(self, other):
    return cmp(self.value, other.value) in (-1, 0)

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

  def __ne__(self, other):
    return cmp(self.value, other.value) != 0

  def __gt__(self, other):
    return cmp(self.value, other.value) == 1

  def __ge__(self, other):
    return cmp(self.value, other.value) in (1, 0)

  def __iadd__(self, other) :
    self.value += other.value
    self.key = fizzbuzz(self.value)
    return self

  def __isub__(self, other) :
    self.value -= other.value
    self.key = fizzbuzz(self.value)
    return self

  def __imul__(self, other) :
    self.value *= other.value
    self.key = fizzbuzz(self.value)
    return self

  def __imod__(self, other) :
    self.value %= other.value
    self.key = fizzbuzz(self.value)
    return self

  def __idiv__(self, other) :
    self.value /= other.value
    self.key = fizzbuzz(self.value)
    return self

  def __ipow__(self, other) :
    self.value **= other.value
    self.key = fizzbuzz(self.value)
    return self

Wenn Sie den folgenden Code ausführen

fizz = FizzBuzzNumber(3)
buzz = FizzBuzzNumber(5)
print 'fizz + buzz = ', fizz + buzz
print 'fizz - buzz = ', fizz - buzz
print 'fizz * buzz = ',  fizz * buzz
print 'fizz / buzz = ', fizz / buzz
print 'fizz % buzz = ', fizz % buzz
print 'fizz ** buzz = ', fizz ** buzz
print 'fizz > buzz: ', fizz > buzz
print 'fizz < buzz: ', fizz < buzz
print 'fizz == buzz: ', fizz == buzz
print 'fizz != buzz: ', fizz != buzz
print 'fizz <= buzz: ', fizz <= buzz
print 'fizz >= buzz: ', fizz >= buzz
print 'fizz():', fizz()
fizz += buzz
print 'fizz += buzz => fizz() = ' , fizz()
fizz -= buzz
print 'fizz -= buzz => fizz() = ' , fizz()
fizz *= buzz
print 'fizz *= buzz => fizz() = ' , fizz()
fizz /= buzz
print 'fizz /= buzz => fizz() = ' , fizz()
fizz %= buzz
print 'fizz %= buzz => fizz() = ', fizz()
fizz **= buzz
print 'fizz **= buzz => fizz() = ', fizz()

Das folgende Ergebnis wird ausgegeben.

fizz + buzz =  8
fizz - buzz =  -2
fizz * buzz =  FizzBuzz
fizz / buzz =  FizzBuzz
fizz % buzz =  Fizz
fizz ** buzz =  Fizz
fizz > buzz =  False
fizz < buzz =  True
fizz == buzz:  False
fizz != buzz:  True
fizz <= buzz:  True
fizz >= buzz:  False
fizz(): Fizz
fizz += buzz => fizz() =  8
fizz -= buzz => fizz() =  Fizz
fizz *= buzz => fizz() =  FizzBuzz
fizz /= buzz => fizz() =  Fizz
fizz %= buzz => fizz() =  Fizz
fizz **= buzz => fizz() =  Fizz

Funktion zur Quantifizierung

Danach habe ich eine Klasse erstellt, um FizzBuzz zu quantifizieren, die in einer zufälligen Spalte angezeigt wurde.

class FizzBuzzCounter:
  def __init__(self, f_start, b_start, fb_start):
    self.f = f_start
    self.b = b_start
    self.fb = fb_start

  def get_value(self, s):
    if s == 'FizzBuzz': 
      return self.fb
    elif s == 'Buzz': 
      return self.b
    elif s == 'Fizz': 
      return self.f
    else: 
      return s

  def next(self, s):
    if s == 'FizzBuzz': 
      self.fb += 15
    elif s == 'Buzz': 
      if (self.b % 15) == 10:
         self.b += 10
      else:
         self.b += 5
    elif s == 'Fizz': 
      if (self.f % 15) == 12:
         self.f += 6
      else:
         self.f += 3
    else: 
      pass

Funktion zum Ersetzen der FizzBuzz-Spalte

Mit den beiden oben genannten Klassen habe ich eine Funktion erstellt, die eine Spalte erstellt, indem die Elemente der angegebenen FizzBuzz-Spalte durch eine Instanz der FizzBuzzNumber-Klasse ersetzt wurden.

def recreate_fizzbuzz_seq(seq):
  counter = FizzBuzzCounter(3,5,15)
  ret = []
  for e in seq:
   ret.append(FizzBuzzNumber(counter.get_value(e)))
   counter.next(e)
  return ret

Geben Sie danach einfach die obige neue Spalte in die zuletzt erstellte Schnellsortierfunktion ein.

Schnelle Sortierfunktion, die zuletzt erstellt wurde

def pivot(target, i, j):
  k = i + 1
  while k <= j and target[i] == target[k]: k += 1
  if k > j: return -1
  if target[i] >= target[k]: 
    return i
  else:
    return k

def partition(target, i, j, x):
  l, r = i, j
  while l <= r:
    while l <= j and target[l] < x: l += 1
    while r >= i and target[r] >= x: r -= 1
    if l > r: break
    target[l], target[r] = target[r], target[l]
    l, r = l + 1, r - 1
  return l

def quick_sort(target,i ,j):
  if i == j: return 
  p = pivot(target, i, j)
  if p != -1:
    k = partition(target, i, j, target[p])
    quick_sort(target, i, k-1)
    quick_sort(target, k, j)

Eine Funktion, die eine zufällige FizzBuzz-Spalte erstellt

def make_random_fizzbuzz(start=1,finish=100):
  seq = range(start,finish+1)
  random_fizzbuzz = []
  while seq:
    random_fizzbuzz.append(fizzbuzz(seq.pop(random.randint(0,len(seq)-1))))
  return random_fizzbuzz

Hauptfunktion

Eine Funktion, die die angegebene FizzBuzz-Spalte recreate_fizzbuzz_seq () gibt, um eine neue Spalte zu erstellen und die neue Spalte schnell zu sortieren

def fizzbuzz_sort(target):
  newtarget = recreate_fizzbuzz_seq(target)
  quick_sort(newtarget,0,len(newtarget)-1)
  return newtarget

Beginnen Sie wie folgt.

fizzbuzz_sort(make_random_fizzbuzz())

Impressionen

Ich mache so eine dumme Sache. Ich denke auch, dass es für die neue FizzBuzzNumber-Instanz besser gewesen wäre, __add__ () usw. zurückzugeben.

Recommended Posts

Sortieren Sie zufällige FizzBuzz-Spalten mit schneller Sortierung
Lernen Sie das schnelle Sortieren, um zufällige FizzBuzz-Spalten zu sortieren
Sortieren Sie Namen mit dem Zufallsmodul von Python
Ich habe versucht, eine zufällige FizzBuzz-Spalte mit Blasensortierung zu sortieren.
FizzBuzz in Python3
Schnelle Sortierung ohne Sortierung
Fizzbuzz mit Ausnahmebehandlung
Sortieren Sie große Dateien mit Python
Blasensortierung mit flauschiger Animation