Библиотека для рисования [закрытых] музыкальных нот

Словарь может содержать много значений, если ваши диапазоны не слишком широки, вы можете создать словарь, аналогичный тому, который был у вас для условий равенства, расширяя каждый диапазон программно:

from collections import defaultdict

ranges   = {(0,10):'A', (10,30):'B', (30,50):'C',(50,90):'D'}
valueMap = defaultdict(lambda:'E')
for r,letter in ranges.items(): 
    valueMap.update({ v:letter for v in range(r[0],r[1]) })

valueMap[701] # 'E'
valueMap[7] # 'A'

Вы также можете просто удалить лишние условия из оператора if / elif и отформатировать его немного по-другому. Это почти выглядело бы как заявление случая:

if   score < 10 : cat = 'A'
elif score < 30 : cat = 'B'
elif score < 50 : cat = 'C'
elif score < 90 : cat = 'D'
else            : cat = 'E'

, чтобы избежать повторения счета < Вы можете определить функцию case и использовать ее со значением:

score = 43
case = lambda x: score < x
if   case(10): cat = "A"
elif case(30): cat = "B"
elif case(50): cat = "C"
elif case(90): cat = "D"
else         : cat = "E"
print (cat) # 'C'

Вы можете обобщить это, создав функцию switch, которая возвращает функцию «case», которая применяется к тестовому значению с общим шаблоном сравнения:

def switch(value):
    def case(check,lessThan=None):
        if lessThan is not None:
            return (check is None or check <= value) and value < lessThan
        if type(value) == type(check): return value == check
        if isinstance(value,type(case)): return check(value)
        return value in check
    return case

Эта универсальная версия допускает всевозможные комбинации:

score = 35
case = switch(score)
if   case(0,10)         : cat = "A"
elif case([10,11,12,13,14,15,16,17,18,19]): 
                          cat = "B"
elif score < 30         : cat = "B" 
elif case(30) \
  or case(range(31,50)) : cat = 'C'
elif case(50,90)        : cat = 'D'
else                    : cat = "E"
print(cat) # 'C'

И есть еще один способ использования лямбда-функции, когда все, что вам нужно сделать, это вернуть значение: [1112 ]

score = 41
case  = lambda x,v: v if score<x else None
cat   = case(10,'A') or case(20,'B') or case(30,'C') or case(50,'D') or 'E' 
print(cat) # "D"

Этот последний также может быть выражен с использованием понимания списка и таблицы отображения:

mapping = [(10,'A'),(30,'B'),(50,'C'),(90,'D')]
scoreCat = lambda s: next( (L for x,L in mapping if s<x),"E" )

score = 37
cat = scoreCat(score) 
print(cat) #"D"
10
задан jam 22 February 2013 в 13:12
поделиться

4 ответа

Вы можете попробовать это:

http://www.archiwistykamuzyczna.pl/index.php?article=download&lang=en#psamcontrollibrary

Это простая библиотека, написанная на C # для отображение заметок. Он ограничен только одним нотным станом, но поддерживает много голосов на одном нотном стане. Формат ввода - MusicXml, но вы также можете добавлять заметки программно.

Вот статья о библиотеке управления PSAM на CodeProject: http://www.codeproject.com/KB/miscctrl/psamcontrollibrary.aspx

1
ответ дан 4 December 2019 в 00:27
поделиться

Вы определенно захотите изучить Lilypond, широко подтвержденный как лучший выбор для музыкального набора. Это - открытый исходный код и имеет все виды выходных форматов и очень scriptable. Было бы довольно легко записать Вашу собственную обертку C# вокруг этого. Пример произвел:


(источник: lilypond.org)

8
ответ дан 4 December 2019 в 00:27
поделиться

Используйте MusicXML. Существует привязка C++.

Rosegarden может экспортировать MusicXML в PDF или PS.

3
ответ дан 4 December 2019 в 00:27
поделиться

Можно попытаться извлечь соответствующие нормы из Rosegarden, хотя это является очень Определенным для QT.

0
ответ дан 4 December 2019 в 00:27
поделиться
Другие вопросы по тегам:

Похожие вопросы: