diff options
Diffstat (limited to 'benchmark')
-rw-r--r-- | benchmark/README.md | 15 | ||||
-rw-r--r-- | benchmark/data.toml | 128 | ||||
-rw-r--r-- | benchmark/requirements.txt | 13 | ||||
-rw-r--r-- | benchmark/run.py | 66 |
4 files changed, 222 insertions, 0 deletions
diff --git a/benchmark/README.md b/benchmark/README.md new file mode 100644 index 0000000..3661f32 --- /dev/null +++ b/benchmark/README.md @@ -0,0 +1,15 @@ +# Benchmark + +## Running + +### Against the local Tomli-W state + +```bash +tox -e benchmark +``` + +### Against the latest Tomli-W PyPI release + +```bash +tox -e benchmark-pypi +``` diff --git a/benchmark/data.toml b/benchmark/data.toml new file mode 100644 index 0000000..882b60f --- /dev/null +++ b/benchmark/data.toml @@ -0,0 +1,128 @@ +addition-used = false +afraid-boiling-draconian = 1916-12-15T11:26:42+11:26 +boiling-whip = 12:23:17.000129 +charming = 16771 +close-unbecoming = 14:49:02 +contain-terrible-neck = 1928-11-07T06:30:56 +creature = 0.4857 +crowded-profuse-capable = 1932-05-28 +deserted-cross-creature = 1931-12-26T04:31:04 +deserted-heavy = [ 2014-02-08, 1984-03-16, 1910-08-05 ] +fabulous = 0.3388 +ghost-birds-legal = 1989-09-02 +grandfather-weary = 10216 +haircut-dreary-broken = 'unadvised rejoice lewd crime grandfather rice imperfect' +harm-snow = 0.6724 +leather-aromatic-rabbit = false +license-harm = 1987-08-15T15:30:51+03:24 +naughty-self-close = 1916-09-21T01:53:27-02:59 +neck = 29653 +neck-crime-wistful = 1998-12-07 +rest-afraid = [ + 1912-06-23T07:00:07-07:46, # this is a datetime + 1910-11-17T13:10:34, # pretty sure this is also a datetime + 2014-08-03T04:37:12-06:36, # and this + 1966-11-22T18:08:23+06:10, # and this + 1985-03-01T08:11:38, # what about this? + 1976-09-04T20:46:46+00:29, # yes that also + 1964-05-18T20:13:27-01:25, # ... + 1961-10-14T11:03:51.011555+06:23, + 2005-07-13T02:57:15-01:46, # wonder how many comments there are typically in + 2007-02-01T17:09:54-08:45, # a TOML file of this size + 1952-03-06T09:15:04+01:44, + 1962-12-25T23:00:11+04:28 +] +rotten-best = 0.0325 +run-curious = true +run-meaty = 04:40:20.003312 +scintillating-cream = 0.2604 +sisters-playground = 'week spiritual pause insidious uptight' +spiritual-borrow-messy = 16:49:32 +surprise-jail-babies = 2008-01-01 +title-unbiased = 1958-10-08 +unbecoming-scene-lewd = true +worried-spicy = 23:03:54 + +[contain] +ghost = 0.2471 +tank-lackadaisical = 1945-02-18T22:22:27+01:41 + + [contain.righteous-imperfect-remarkable] + ticket = 0.2412 + voyage = 'prefer silky night draconian three dreary decisive' + wilderness-draconian = 04:58:17 + + [contain.righteous-imperfect-remarkable.deeply-night-gold] + legal = 1981-07-04 + righteous = [ false, true, false, false, true ] + wilderness = 1900-12-24 + +[crime] +boiling-excuse-incandescent = 31173 +flat-rejoice = 0.8682 +furtive = 6866 +heavy-memory = 5545 +lackadaisical-terrible-overjoyed = [ 'harm acceptable naughty pause', 'page anxious threatening lewd' ] +reject-aromatic = [ false, true, true, true, false, true ] +reject-naughty = 11229 +scintillating-bake-harm = 0.8258 + +[license-bat] +adorable-blind-string = 1961-08-14 +bat = 1939-10-28 +blind-wilderness = 2004-07-14 + +[rapid] +borrow = true +jail-weary-furtive = 'room' +protective-sulky = 4737 +room-decisive-unbiased = 1998-11-01T12:23:58 +soap = 1985-05-06 +sprout-rich = 0.6026 + + [rapid.clean-leather] + blood-snow-mark = true + equable = 0.2923 + fabulous = 1979-07-24T00:53:39+06:22 + glorious-threatening = true + lewd-dull = 02:40:53.027288 + +[run-overjoyed] +creature-cheerful = 11071 +respect-history-anxious = 0.4637 +vessel = 'curious' + +[inline-tables] +table1 ={ the-text-in-this = 'file is weeiiird' , autogenerated-perhaps= 1199999 , subtableee = {blii=false}} +table2 = { arr = [ { id = 0 }, { id = 1}, { id = 2} ] } + +[[dynamic-arrays.products]] +name = "juusto" + [[dynamic-arrays.products]] + name = "tee \t\t kannu" +[[dynamic-arrays.products]] +name = "\n\nkahvi" + [[dynamic-arrays.products]] + name = "\"riisi\"" +[[dynamic-arrays.products]] +name = "puuro \\ riisipuuro" + + +# Fusce sit amet risus vel sapien vestibulum interdum. Aliquam finibus +# finibus nibh, sed mattis nulla lacinia in. Nunc ac volutpat massa, +# at fringilla dui. In dignissim pellentesque luctus. Cras ac ex metus. +# Duis ut molestie augue. Donec vitae nulla massa. Sed blandit diam sit +# amet mauris posuere consectetur. + +[multiline-strings] +literal-str = ''' +Liirum laarum liirum laarum. +Liirum laarum liirum laarum. +Liirum laarum liirum laarum. +''' +basic-str = """\ + Escape whitespace. \ + + + Liirum laarum liirum laarum.\ueeee\U000eeeee\u1234 +""" diff --git a/benchmark/requirements.txt b/benchmark/requirements.txt new file mode 100644 index 0000000..93d19c1 --- /dev/null +++ b/benchmark/requirements.txt @@ -0,0 +1,13 @@ +# NOTE +# Tomli-W itself is not included here because tox is used to read +# this file and install the deps, and it handles the Tomli-W +# installation separately. +pytomlpp +toml +tomlkit +qtoml +# comment out TOML v1.0.0 incompatible rtoml +#rtoml + +# for reading data.toml +tomli diff --git a/benchmark/run.py b/benchmark/run.py new file mode 100644 index 0000000..a9a7713 --- /dev/null +++ b/benchmark/run.py @@ -0,0 +1,66 @@ +from __future__ import annotations
+
+from collections.abc import Callable
+from pathlib import Path
+import timeit
+
+import pytomlpp
+import qtoml
+
+# import rtoml
+import toml
+import tomli
+import tomlkit
+
+import tomli_w
+
+test_data_file = Path(__file__).parent / "data.toml"
+test_data = tomli.loads(test_data_file.read_bytes().decode())
+# Make the game fair for tomlkit by converting `test_data` to a
+# tomlkit native type before measurements.
+tomlkit_test_data = tomlkit.item(test_data)
+
+
+def benchmark(
+ name: str,
+ run_count: int,
+ func: Callable,
+ col_width: tuple,
+ compare_to: float | None = None,
+) -> float:
+ placeholder = "Running..."
+ print(f"{name:>{col_width[0]}} | {placeholder}", end="", flush=True)
+ time_taken = timeit.timeit(func, number=run_count)
+ print("\b" * len(placeholder), end="")
+ time_suffix = " s"
+ print(f"{time_taken:{col_width[1]-len(time_suffix)}.3g}{time_suffix}", end="")
+ if compare_to is None:
+ print(" | baseline (100%)", end="")
+ else:
+ delta = compare_to / time_taken
+ print(f" | {delta:.2%}", end="")
+ print()
+ return time_taken
+
+
+def run(run_count: int) -> None:
+ col_width = (10, 10, 28)
+ col_head = ("parser", "exec time", "performance (more is better)")
+ print(f"Dumping test data to a string {run_count} times:")
+ print("-" * col_width[0] + "---" + "-" * col_width[1] + "---" + col_width[2] * "-")
+ print(
+ f"{col_head[0]:>{col_width[0]}} | {col_head[1]:>{col_width[1]}} | {col_head[2]}"
+ )
+ print("-" * col_width[0] + "-+-" + "-" * col_width[1] + "-+-" + col_width[2] * "-")
+ # fmt: off
+ baseline = benchmark("pytomlpp", run_count, lambda: pytomlpp.dumps(test_data), col_width) # noqa: E501
+ # benchmark("rtoml", run_count, lambda: rtoml.dumps(test_data), col_width, compare_to=baseline) # noqa: E501
+ benchmark("tomli", run_count, lambda: tomli_w.dumps(test_data), col_width, compare_to=baseline) # noqa: E501
+ benchmark("toml", run_count, lambda: toml.dumps(test_data), col_width, compare_to=baseline) # noqa: E501
+ benchmark("tomlkit", run_count, lambda: tomlkit.dumps(tomlkit_test_data), col_width, compare_to=baseline) # noqa: E501
+ benchmark("qtoml", run_count, lambda: qtoml.dumps(test_data), col_width, compare_to=baseline) # noqa: E501
+ # fmt: on
+
+
+if __name__ == "__main__":
+ run(5000)
|