Skip to content

Commit

Permalink
more tests
Browse files Browse the repository at this point in the history
  • Loading branch information
cootshk committed Nov 2, 2023
1 parent 8507639 commit 03c9c05
Show file tree
Hide file tree
Showing 5 changed files with 75 additions and 38 deletions.
35 changes: 14 additions & 21 deletions tables.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
"""

# check for python version
from typing import Iterable, override, Any, Optional, overload, Callable
from typing import Iterable, Any, Optional, overload, Callable
import sys
if sys.version_info < (3, 12):
print("This script requires Python 3.12+")
Expand All @@ -27,7 +27,7 @@ class Table(Iterable):
Table(1,2,3) == Table([1,2,3]) # True
len(Table("a", "b", "c", four="d", five="e")) # 5
Types:
KeyValue (str | int): Any key value, either a string or an int. A string is used for dictionary keys,
KeyValue (str | int): Any key value, either a string or an int. A string is used for dictionary keys,
and an int is used for list indices.
"""
type KeyValue = str | int
Expand Down Expand Up @@ -64,6 +64,7 @@ def find_keys(self, value: Any, /) -> KeyValue: ...

@overload
def find_keys[default](
# type: ignore
self, value: Any, /, *, default: Any = None) -> list[KeyValue] | default: ...

@overload
Expand Down Expand Up @@ -109,13 +110,12 @@ def sort(self, *, key: Callable, reverse: bool) -> "Table": ...
# sort
###############################################

@override
def __init__(self, *args: Optional[Any], **kwargs: Optional[Any]):
"""The init function.
"""The init function.
Args:
*list_values (list[Any] | Any): The list values. If there is only one argument, then that is set to the list.
**dict_values (dict[str, Any] | Any): The dict values. If there is only one argument, then that is set to the dict.
Examples:
see the Table() documentation
Expand Down Expand Up @@ -159,7 +159,7 @@ def __setitem__(self, key: KeyValue | Iterable[KeyValue], value: Any):
elif isinstance(key, int):
self.list[key] = value
elif isinstance(key, Iterable):
for i, j, _ in zip(key, value):
for i, j in zip(key, value):
self[i] = j
else:
raise TypeError(f"Table indices must be integers or strings, not {
Expand Down Expand Up @@ -187,7 +187,6 @@ def __delitem__(self, key: KeyValue | Iterable[KeyValue]):
raise TypeError(f"Table indices must be integers or strings, not {
type(key).__name__}")

@override
def __iter__(self) -> Any:
return iter(self.list)

Expand All @@ -200,7 +199,6 @@ def _list_len_(self) -> int:
def _dict_len_(self) -> int:
return len(self.dict)

@override
def __repr__(self) -> str:
if len(self) == 0:
return "Table()"
Expand All @@ -214,19 +212,19 @@ def _unpack_kwargs_to_str_(self) -> str:
ret += f"{k}: {v if not isinstance(v, str) else f"'{v}'"}, "
return ret.removesuffix(", ")

@override
def __str__(self) -> str:
# if len(self) == 0:
# return "<>"
return f"<{(''.join([
f'{x}, ' for x in self.list
])).removesuffix(', ')}, {
self._unpack_kwargs_to_str_()}>".replace(
self._unpack_kwargs_to_str_()}>".replace(
"<, ", "<").replace(
", >", ">")

def __contains__(self, key: str) -> bool:
return (key in self.dict) or (key in self.list)

def find_keys(self, value: Any, /, *, default: Any=None) -> list[KeyValue] | Any:
"""Finds all keys and indices that have a value equal to value.
Expand All @@ -250,7 +248,6 @@ def find_keys(self, value: Any, /, *, default: Any=None) -> list[KeyValue] | Any
return ret[0]
return ret

@override
def append(self, value: Any) -> "Table":
"""Append a value to the end of the list.
Expand All @@ -263,7 +260,6 @@ def append(self, value: Any) -> "Table":
self.list.append(value)
return self

@override
def extend(self, value: Iterable[Any]) -> "Table":
"""Extend the list with another iterable.
Expand All @@ -276,7 +272,6 @@ def extend(self, value: Iterable[Any]) -> "Table":
self.list.extend(value)
return self

@override
def insert(self, index: int, value: Any) -> "Table":
"""Insert a value at a specific index.
Expand All @@ -290,7 +285,6 @@ def insert(self, index: int, value: Any) -> "Table":
self.list.insert(index, value)
return self

@override
def pop(self, index: int = -1) -> Any:
"""Returns a specific value in a list and removes it.
Expand Down Expand Up @@ -351,7 +345,7 @@ def count(self, value: Any, count_list: bool = True, count_dict_keys: bool = Fa
ret += list(self.dict.keys()).count(value) if count_dict_keys else 0
return ret

def foreach(self, func: Callable, /, list_eval: bool =True, dict_eval: bool=True) -> list[Any] | Any:
def foreach(self, func: Callable, /, list_eval: bool = True, dict_eval: bool=True) -> list[Any] | Any:
"""Call a function on each item in the table.
Args:
Expand All @@ -371,13 +365,13 @@ def foreach(self, func: Callable, /, list_eval: bool =True, dict_eval: bool=True
ret = []
if bool(list_eval):
for i, j in enumerate(self.list):
ret += func(i, j) # type: ignore
print(i, j,func)
ret.append(func(i, j))
if bool(dict_eval):
for k, v in zip(self.dict.keys(), self.dict.values()):
ret += func(k, v) # type: ignore
ret.append(func(k, v)) # type: ignore
return ret if len(ret) > 1 else ret[0] if len(ret) == 1 else None

@override
def __eq__(self, other):
if isinstance(other, Table):
return self.list == other.list and self.dict == other.dict
Expand All @@ -394,8 +388,8 @@ def __add__(self, other: Any) -> "Table":
raise TypeError(
f"unsupported operand type(s) for +: 'Table' and '{type(other).__name__}'")

@override
def sort(self, *, key: Optional[Callable] = None, reverse: bool=False) -> "Table":
# type: ignore
def sort(self, *, key: Any = None, reverse: bool =False) -> "Table":
"""Sorts the list in place.
Args:
Expand All @@ -408,7 +402,6 @@ def sort(self, *, key: Optional[Callable] = None, reverse: bool=False) -> "Table
self.list.sort(key=key, reverse=reverse)
return self

@override
def __bool__(self) -> bool:
return bool(self.list) or bool(self.dict)

Expand Down
16 changes: 16 additions & 0 deletions tests/test_foreach.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""Testing table.foreach() method.
This is a **very dangerous** method, so it is tested separately.
"""
from ..tables import Table


def test_tables() -> None:
"""The actual tests."""
tbl = Table(1, 2, 3)
assert isinstance(tbl.foreach(lambda x, y: y),
list), "Foreach test 1 failed!"
assert tbl.foreach(lambda x, y: [x, y, True]) == [
[0, 1, True],
[1, 2, True],
[2, 3, True]
], "Foreach test 2 failed!"
17 changes: 17 additions & 0 deletions tests/test_inheritance.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
"""Testing list and dict methods of tables"""
from ..tables import Table

def test_inheritance() -> None:
"""The actual tests.
Returns:
Optional[bool]: True or None if the test passes, False or errors if it fails.
"""
assert Table(1,3,2).sort() == Table(1,2,3), "Inheritance test 1 failed!"
assert bool(Table(1,2,3)), "Inheritance test 2 failed!"
assert not bool(Table()), "Inheritance test 3 failed!"
assert Table(1,2,3).list == [1,2,3], "Inheritance test 4 failed!"
assert Table(1,2,3).dict == {}, "Inheritance test 5 failed!"
x = Table(1,2,3)
assert x.pop(1) == 2, "Inheritance test 6 failed!"
assert x == Table(1,3), "Inheritance test 7 failed!"
23 changes: 6 additions & 17 deletions tests/test_main.py
Original file line number Diff line number Diff line change
@@ -1,13 +1,7 @@
"""Unit tests for main.py
"""

try:
from ..tables import Table
except:
try:
from tables import Table
except:
from .tables import Table
from ..tables import Table

def test_tables():
"""Unit tests for Table() class
Expand All @@ -22,13 +16,8 @@ def test_tables():
assert repr(x) == "Table([1, 2, 3]; {'foo': 'bar', 'spam': 'eggs'})", "Test 4 failed!"
assert x.list == [1,2,3], "Test 5 failed!"
assert x.dict == {"foo":"bar", "spam":"eggs"}, "Test 6 failed!"
assert x == Table(1,2,3, foo="bar", spam="eggs"), "Test 7 failed!"
assert x + Table(4,5,6) == Table(1,2,3,4,5,6, foo="bar", spam="eggs"), "Test 8 failed!"
assert x.foreach(
lambda k, v: [k, v]) == [0, 1, 1, 2, 2, 3, "foo", "bar", "spam", "eggs"
], "Test 9 failed!"
assert Table(1,3,2).sort() == Table(1,2,3), "Test 10 failed!"
assert bool(Table(1,2,3)), "Test 11 failed!"
assert not bool(Table()), "Test 12 failed!"
#congrats, the code works!
print("All tests passed!")
assert x[0] == 1, "Test 7 failed!"
assert x[1] == 2, "Test 8 failed!"
assert x[2] == 3, "Test 9 failed!"
assert x["foo"] == "bar", "Test 10 failed!"
assert x["spam"] == "eggs", "Test 11 failed!"
22 changes: 22 additions & 0 deletions tests/test_operands.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""Testing table operands, like +, ==, etc."""
from ..tables import Table


def test_operands() -> None:
"""The actual tests."""
assert Table() + Table() == Table(), "Operands test 1 failed!"
assert Table(1, 2, 3) + Table(4, 5, 6) == Table(1, 2,
3, 4, 5, 6), "Operands test 2 failed!"
assert Table(1, 2, 3) != Table(
1, 2, 3, foo="bar"), "Operands test 3 failed!"
assert Table(1, 2, 3) == Table(1, 2, 3), "Operands test 4 failed!"
assert Table(1, 2, 3) != Table(1, 2, 4), "Operands test 5 failed!"
assert Table(foo="bar") == Table(foo="bar"), "Operands test 6 failed!"
assert Table(foo="bar") != Table(foo="baz"), "Operands test 7 failed!"
assert Table(1, 2, 3) + Table(foo="bar") == Table(1, 2,
3, foo="bar"), "Operands test 8 failed!"
x = Table()
x.append(2)
x["foo"] = "bar"
assert x == Table(2, foo="bar"), "Operands test 9 failed!"
assert id(x) != id(Table(2, foo="bar")), "Operands test 10 failed!"

0 comments on commit 03c9c05

Please sign in to comment.