Skip to content
Snippets Groups Projects
Select Git revision
  • 9e671a06873d9623623ecc7d29636c7673456d5d
  • devel default
  • master
  • fo
  • jirka/typing
  • fo-base
  • mj/submit-images
  • jk/issue-96
  • jk/issue-196
  • honza/add-contestant
  • honza/mr7
  • honza/mrf
  • honza/mrd
  • honza/mra
  • honza/mr6
  • honza/submit-images
  • honza/kolo-vs-soutez
  • jh-stress-test-wip
  • shorten-schools
19 results

org_contest_import.html

Blame
  • gen-k1.py 1.82 KiB
    #!/usr/bin/python3
    # Generování všech posloupností 0 a 1 délky n, ve kterých je právě k jedniček
    # Posloupnosti vypisujeme v lexikografickém pořadí
    
    ### Rekurzivní řešení: generujeme všechny posloupnosti délky s prefixem p,
    ### do kterých potřebujeme přidat n cifer, z nichž k jsou jedničky.
    
    def genk1(n, k, p=[]):
        if n == 0:
            print("".join(map(str, p)))
        else:
            # 0 můžeme přidat, pokud zbude dost pozic na to, aby se do nich
            # vešly všechny zbývající 1.
            if k < n:
                genk1(n-1, k, p + [0])
    
            # 1 můžeme přidat, pokud jsme ještě všechny nespotřebovali.
            if k > 0:
                genk1(n-1, k-1, p + [1])
    
    ### A opět můžeme podobným způsobem počítat, kolik takových posloupností existuje:
    
    def countk1(n, k):
        if n == 0:
            return 1
        else:
            result = 0
            if k < n:
                result += countk1(n-1, k)
            if k > 0:
                result += countk1(n-1, k-1)
            return result
    
    ### Počítací funkce je ovšem pomalá: výsledek je kombinační číslo (poznáváte
    ### v naší funkci součtový vzorec z Pascalova trojúhelníku?) a nasčítáme ho
    ### postupně z jedniček. Přitom "n nad n/2" je řádově 2^n / √n. Stejně jako
    ### u příkladu s Fibonacciho čísly si můžeme mezivýsledky pamatovat a tím
    ### výpočet zrychlit na O(n^2). Mimochodem, uměli byste to rychleji, aniž
    ### byste potřebovali mezivýsledky řádově větší než výsledek?
    
    mem = {}        # Slovník, kde klíče jsou tuply (n,k)
    
    def countk1b(n, k):
        if (n,k) not in mem:
            if n == 0:
                result = 1
            else:
                result = 0
                if k < n:
                    result += countk1b(n-1, k)
                if k > 0:
                    result += countk1b(n-1, k-1)
            mem[(n,k)] = result
        return mem[(n,k)]