Fixed some bugs and added new tests
New test_multi_03 can be used to test multiple variables at once. Based on new collect function that can be used to collect n variables from parsed Ziffers.
This commit is contained in:
13
tests/test_multi_03.py
Normal file
13
tests/test_multi_03.py
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
""" Test cases for the parser """
|
||||||
|
import pytest
|
||||||
|
from ziffers import zparse
|
||||||
|
|
||||||
|
@pytest.mark.parametrize(
|
||||||
|
"pattern,expected",
|
||||||
|
[
|
||||||
|
("1 2 3", [[1, 2, 3], [0.25,0.25,0.25]]),
|
||||||
|
("q2 eq3 e.4", [[2, 3, 4], [0.25,0.375,0.1875]]),
|
||||||
|
],
|
||||||
|
)
|
||||||
|
def test_multi_var(pattern: str, expected: list):
|
||||||
|
assert zparse(pattern).collect(6, keys=["pitch_class", "duration"]) == [item*2 for item in expected]
|
||||||
@ -2,8 +2,6 @@
|
|||||||
import pytest
|
import pytest
|
||||||
from ziffers import scale
|
from ziffers import scale
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"name,expected",
|
"name,expected",
|
||||||
[
|
[
|
||||||
@ -1,6 +1,6 @@
|
|||||||
""" Test cases for the parser """
|
""" Test cases for the parser """
|
||||||
import pytest
|
import pytest
|
||||||
from ziffers import zparse, collect
|
from ziffers import zparse, get_items
|
||||||
|
|
||||||
# pylint: disable=missing-function-docstring, line-too-long, invalid-name
|
# pylint: disable=missing-function-docstring, line-too-long, invalid-name
|
||||||
|
|
||||||
@ -52,7 +52,7 @@ def test_parsing_text(pattern: str):
|
|||||||
],
|
],
|
||||||
)
|
)
|
||||||
def test_pitch_classes(pattern: str, expected: list):
|
def test_pitch_classes(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"pitch_class") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"pitch_class") == expected*2
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
@ -64,7 +64,7 @@ def test_pitch_classes(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_pitch_octaves(pattern: str, expected: list):
|
def test_pitch_octaves(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"octave") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"octave") == expected*2
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
@ -77,7 +77,7 @@ def test_pitch_octaves(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_subdivisions(pattern: str, expected: list):
|
def test_subdivisions(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"duration") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"duration") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -89,7 +89,7 @@ def test_subdivisions(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_repeats(pattern: str, expected: list):
|
def test_repeats(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"note") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"note") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -104,7 +104,7 @@ def test_repeats(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_repeat_durations(pattern: str, expected: list):
|
def test_repeat_durations(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"duration") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"duration") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -130,7 +130,7 @@ def test_looping_durations(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_measure_durations(pattern: str, expected: list):
|
def test_measure_durations(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"duration") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"duration") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -139,7 +139,7 @@ def test_measure_durations(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_measure_octaves(pattern: str, expected: list):
|
def test_measure_octaves(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"octave") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"octave") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -148,7 +148,7 @@ def test_measure_octaves(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_rest(pattern: str, expected: list):
|
def test_rest(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"duration") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"duration") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -157,7 +157,7 @@ def test_rest(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_ranges(pattern: str, expected: list):
|
def test_ranges(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"note") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"note") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -166,7 +166,7 @@ def test_ranges(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_romans(pattern: str, expected: list):
|
def test_romans(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"note") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"note") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -177,7 +177,7 @@ def test_romans(pattern: str, expected: list):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
def test_romans_pcs(pattern: str, expected: list):
|
def test_romans_pcs(pattern: str, expected: list):
|
||||||
assert collect(zparse(pattern),len(expected)*2,"pitches") == expected*2
|
assert get_items(zparse(pattern),len(expected)*2,"pitches") == expected*2
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
"pattern,expected",
|
"pattern,expected",
|
||||||
@ -188,4 +188,4 @@ def test_romans_pcs(pattern: str, expected: list):
|
|||||||
)
|
)
|
||||||
def test_cycles(pattern: str, expected: list):
|
def test_cycles(pattern: str, expected: list):
|
||||||
zparse.cache_clear() # Clear cache for cycles
|
zparse.cache_clear() # Clear cache for cycles
|
||||||
assert collect(zparse(pattern),4,"note") == expected
|
assert get_items(zparse(pattern),4,"note") == expected
|
||||||
@ -1,6 +1,5 @@
|
|||||||
from .parser import *
|
from .parser import *
|
||||||
from .mapper import *
|
from .mapper import *
|
||||||
from .classes import *
|
|
||||||
from .common import *
|
from .common import *
|
||||||
from .defaults import *
|
from .defaults import *
|
||||||
from .scale import *
|
from .scale import *
|
||||||
|
|||||||
@ -133,6 +133,10 @@ class Event(Item):
|
|||||||
|
|
||||||
duration: float = field(default=None)
|
duration: float = field(default=None)
|
||||||
|
|
||||||
|
def get_duration(self):
|
||||||
|
"""Getter for duration"""
|
||||||
|
return self.duration
|
||||||
|
|
||||||
|
|
||||||
@dataclass
|
@dataclass
|
||||||
class Rest(Event):
|
class Rest(Event):
|
||||||
@ -202,10 +206,6 @@ class Pitch(Event):
|
|||||||
"""Getter for pitche"""
|
"""Getter for pitche"""
|
||||||
return self.pitch_class
|
return self.pitch_class
|
||||||
|
|
||||||
def get_duration(self):
|
|
||||||
"""Getter for duration"""
|
|
||||||
return self.duration
|
|
||||||
|
|
||||||
def update_note(self, force: bool = False):
|
def update_note(self, force: bool = False):
|
||||||
"""Update note if Key, Scale and Pitch-class are present"""
|
"""Update note if Key, Scale and Pitch-class are present"""
|
||||||
if (
|
if (
|
||||||
|
|||||||
@ -155,3 +155,25 @@ class Ziffers(Sequence):
|
|||||||
for val in self.evaluated_values
|
for val in self.evaluated_values
|
||||||
if isinstance(val, (Pitch, Chord))
|
if isinstance(val, (Pitch, Chord))
|
||||||
]
|
]
|
||||||
|
|
||||||
|
def collect(self, num: int = None, keys: str | list = None) -> list:
|
||||||
|
"""Collect n items from parsed Ziffers"""
|
||||||
|
if num is None:
|
||||||
|
num = len(self.evaluated_values)
|
||||||
|
if keys is None or isinstance(keys, str):
|
||||||
|
keys = [keys]
|
||||||
|
all_items = []
|
||||||
|
values = []
|
||||||
|
for key in keys:
|
||||||
|
for i in range(num):
|
||||||
|
if key is not None:
|
||||||
|
values.append(getattr(self[i], key, None))
|
||||||
|
else:
|
||||||
|
values.append(self[i])
|
||||||
|
all_items.append(values)
|
||||||
|
values = []
|
||||||
|
if len(all_items) > 1:
|
||||||
|
return all_items
|
||||||
|
if len(all_items) == 1:
|
||||||
|
return all_items[0]
|
||||||
|
return None
|
||||||
|
|||||||
@ -357,8 +357,10 @@ class ListOperation(Sequence):
|
|||||||
"""Vertical arpeggio operation, eg. (135)@(q 1 2 021)"""
|
"""Vertical arpeggio operation, eg. (135)@(q 1 2 021)"""
|
||||||
left = _filter_operation(left, options)
|
left = _filter_operation(left, options)
|
||||||
right = _filter_operation(right, options)
|
right = _filter_operation(right, options)
|
||||||
left = list(left.evaluate_tree(options))
|
if not isinstance(left,list):
|
||||||
right = list(right.evaluate_tree(options))
|
left = list(left.evaluate_tree(options))
|
||||||
|
if not isinstance(right,list):
|
||||||
|
right = list(right.evaluate_tree(options))
|
||||||
arp_items = []
|
arp_items = []
|
||||||
|
|
||||||
for item in left:
|
for item in left:
|
||||||
|
|||||||
@ -53,7 +53,6 @@ def z(expr: str, **opts) -> Ziffers:
|
|||||||
"""Shortened method name for zparse"""
|
"""Shortened method name for zparse"""
|
||||||
return zparse(expr, **opts)
|
return zparse(expr, **opts)
|
||||||
|
|
||||||
|
|
||||||
def yield_items(gen: Ziffers, num: int, key: str = None) -> list:
|
def yield_items(gen: Ziffers, num: int, key: str = None) -> list:
|
||||||
"""Yield n items from parsed Ziffers"""
|
"""Yield n items from parsed Ziffers"""
|
||||||
for i in range(num):
|
for i in range(num):
|
||||||
@ -62,7 +61,7 @@ def yield_items(gen: Ziffers, num: int, key: str = None) -> list:
|
|||||||
else:
|
else:
|
||||||
yield gen[i]
|
yield gen[i]
|
||||||
|
|
||||||
def collect(gen: Ziffers, num: int, key: str = None) -> list:
|
def get_items(gen: Ziffers, num: int, key: str = None) -> list:
|
||||||
"""Collect n-item from parsed Ziffers"""
|
"""Get n-item from parsed Ziffers. Functional alternative to Ziffers-object collect method."""
|
||||||
return list(yield_items(gen,num,key))
|
return list(yield_items(gen,num,key))
|
||||||
|
|
||||||
Reference in New Issue
Block a user