peace-performance (Rust) binding for python. To calculate star ratings and performance points for all osu! gamemodes

Overview

peace-performance-python

Fast, To calculate star ratings and performance points for all osu! gamemodes

peace-performance (Rust) binding for python based on PyO3.

Cross-platform support.

Faster than oppai-ng, see the benchmark for details.

Note: This library is not currently uploaded to PypI, you may need to download it locally for compilation and then import it in python.

Minimal Examples

from peace_performance_python.prelude import *

beatmap = await Beatmap.create('path_to_osu_file') # Beatmap can be cached and reused!
result = Calculator(acc=98.8, miss=3).calculate(beatmap) # Calculator can also

Full Examples

import asyncio
import sys

# import all
from peace_performance_python.prelude import *
# or
# from peace_performance_python.beatmap import Beatmap
# from peace_performance_python.calculator import Calculator

from tests import join_beatmap, HITORIGOTO


# Initial Rust logger (optional)
set_log_level('trace')
init_logger()


# Choose a style you like
def calculate_1(beatmap: Beatmap) -> CalcResult:
    return calculate_pp(beatmap, Calculator({'acc': 98.8, 'miss': 3}))


def calculate_2(beatmap: Beatmap) -> CalcResult:
    # --
    c = Calculator()
    c.set_acc(98.8)
    c.set_miss(3)

    # or
    c.acc = 98.8
    c.miss = 3

    # or
    c.setattr('acc', 98.8)
    c.setattr('miss', 3)
    return calculate_pp(beatmap, c)


def calculate_3(beatmap: Beatmap) -> CalcResult:
    c = Calculator()
    c.set_with_dict({'acc': 98.8, 'miss': 3})
    return calculate_pp(beatmap, c)


def calculate_4(beatmap: Beatmap) -> CalcResult:
    return Calculator({'acc': 98.8, 'miss': 3}).calculate(beatmap)


def calculate_5(beatmap: Beatmap) -> CalcResult:
    return Calculator(acc=98.8, miss=3).calculate(beatmap)


async def main():
    path = join_beatmap(HITORIGOTO)
    # Load beatmap
    beatmap = await Beatmap.create(path)
    # Calculate pp
    result = calculate_5(beatmap)
    print('\n***** result:', result)
    print('\n***** result.pp:', result.pp)
    print('\n***** result as dict:', result.attrs_dict)
    print('\n***** result.raw_stars as dict:', result.raw_stars.attrs_dict)
    print('\n***** result.raw_pp as dict:', result.raw_pp.attrs_dict)

if __name__ == '__main__':
    asyncio.run(main())

Running results

 TRACE peace_performance_python::methods::common > function=async_read_file duration=289.1µs
 TRACE peace_performance_python::methods::pp     > function=async_parse_beatmap duration=414µs
 TRACE peace_performance_python::methods::pp     > function=calc_with_any_pp duration=99.6µs
 TRACE peace_performance_python::objects::calculator > function=calc duration=245.4µs

...

***** result.pp: 152.19204711914062

...

***** result as dict: {
    'mode': 0, 
    'mods': 0, 
    'pp': 152.19204711914062, 
    'stars': 5.162832260131836, 
    'raw_pp': {
        'aim': 73.0337905883789, 
        'spd': 31.048368453979492, 
        'str': None, 
        'acc': 45.17241287231445, 
        'total': 152.19204711914062}, 
    'raw_stars': {
        'stars': 5.162832260131836, 
        'max_combo': 476, 
        'ar': 9.0, 
        'n_fruits': None, 
        'n_droplets': None, 
        'n_tiny_droplets': None, 
        'od': 8.5, 
        'speed_strain': 2.0723509788513184, 
        'aim_strain': 2.7511043548583984, 
        'n_circles': 207, 
        'n_spinners': 1
        }
    }

...

Building

This package is intended to be built using rust, maturin or setuptools_rust.

1. Install Rust

posix

curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh

windows

https://static.rust-lang.org/rustup/dist/x86_64-pc-windows-msvc/rustup-init.exe

2. Install python dev dependencies

pip install -r requirements-dev.txt

3. Build native python lib

maturin develop --release

OR

python setup.py develop

Compile to .whl to use pip installation

maturin build --release

OR

python setup.py bdist_wheel

install .whl

# maturin build
pip install target/wheels/<name>.whl

# setup.py build
pip install dist/<name>.whl

Run tests and benchmarks

Once built, you can run the tests and benchmakrs using pytest

pytest

or bench and draw a image

pytest --benchmark-histogram

Run examples

python examples.py

Vs Oppai-ng

peace-performance Python bindings vs C89 oppai-ng.

Fast than oppai, the longer the map, the more obvious the advantages of rust.

peace-performance enables the no_sliders_no_leniency feature to be consistent with oppai's algorithm (faster, but loses precision).

If you need maximum precision (osu-performance) rather than performance, use all_included features.

------------------------------------------------------------------------ benchmark 'bench-oppai-vs-rust': 12 tests -------------------------------------------------------------------------
Name (time in ms)               Min                Max               Mean            StdDev             Median               IQR            Outliers       OPS            Rounds  Iterations
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
test_rust_padoru             1.7768 (1.0)       1.9478 (1.0)       1.8508 (1.0)      0.0400 (1.0)       1.8443 (1.0)      0.0535 (1.0)          28;0  540.3156 (1.0)          87           1
test_oppai_padoru            1.8122 (1.02)      9.7861 (5.02)      1.9889 (1.07)     0.5237 (13.08)     1.9249 (1.04)     0.1314 (2.46)          7;8  502.7874 (0.93)        242           1
test_rust_hitorigoto         2.0610 (1.16)      2.5040 (1.29)      2.1910 (1.18)     0.0657 (1.64)      2.1785 (1.18)     0.0694 (1.30)        95;19  456.4104 (0.84)        418           1
test_oppai_hitorigoto        2.5288 (1.42)      3.7520 (1.93)      2.7401 (1.48)     0.1818 (4.54)      2.7067 (1.47)     0.1176 (2.20)        25;17  364.9477 (0.68)        322           1
test_rust_freedom_dive       3.8093 (2.14)      7.3134 (3.75)      3.9828 (2.15)     0.2293 (5.73)      3.9567 (2.15)     0.0845 (1.58)          4;6  251.0782 (0.46)        241           1
test_rust_sotarks            4.4968 (2.53)      5.1071 (2.62)      4.6848 (2.53)     0.0985 (2.46)      4.6712 (2.53)     0.0965 (1.80)        45;13  213.4562 (0.40)        196           1
test_oppai_freedom_dive      5.6872 (3.20)      7.0520 (3.62)      5.9250 (3.20)     0.2010 (5.02)      5.8822 (3.19)     0.1848 (3.46)         17;7  168.7767 (0.31)        159           1
test_oppai_sotarks           6.1222 (3.45)     16.0620 (8.25)      6.4435 (3.48)     0.8114 (20.27)     6.3351 (3.43)     0.1677 (3.14)         3;10  155.1956 (0.29)        152           1
test_rust_galaxy_burst       6.1535 (3.46)      7.3282 (3.76)      6.4249 (3.47)     0.1903 (4.75)      6.3857 (3.46)     0.1377 (2.57)        21;10  155.6452 (0.29)        148           1
test_oppai_galaxy_burst      8.1627 (4.59)     11.3769 (5.84)      8.5283 (4.61)     0.3584 (8.96)      8.4481 (4.58)     0.2359 (4.41)          9;6  117.2565 (0.22)        110           1
test_rust_unforgiving       12.9719 (7.30)     13.9540 (7.16)     13.2572 (7.16)     0.1567 (3.92)     13.2482 (7.18)     0.1395 (2.61)         16;4   75.4307 (0.14)         71           1
test_oppai_unforgiving      22.4598 (12.64)    35.3505 (18.15)    23.6072 (12.76)    2.4802 (61.97)    22.8837 (12.41)    0.4452 (8.32)          3;4   42.3600 (0.08)         44           1
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Simple Benchmarks

Native vs wrapped beatmap object

Read and parsing time spent on beatmap of different sizes (forgiving is a beatmap over 50 minutes long and takes the longest)

There are also subtle differences in the different calling methods


MIT

pure-peace

You might also like...
Script to calculate delegator epoch returns for all pillars

znn_delegator_calculator Script to calculate estimated delegator epoch returns for all Pillars, so you can delegate to the best one. You can find me o

A weekly dive into commonly used modules in the Rust ecosystem, with story flavor!

The goal of this project is to bring the same concept as PyMOTW to the Rust world. PyMOTW was an invaluable resource for me when I was learning Python years ago, and I hope that I can help someone in a similar way. Each week we'll dive into a module and explore some of the functionality that we can find there while following along the adventures of some colourful characters.

A tool to assist in code raiding in rust
A tool to assist in code raiding in rust

Kodelock a tool to assist in code raiding in rust This tool is designed to be used on a second monitor. This tools will allow you to see a easily read

PyWorkflow(PyWF) - A Python Binding of C++ Workflow

PyWorkflow(PyWF) - A Python Binding of C++ Workflow 概览 C++ Workflow是一个高性能的异步引擎,本项目着力于实现一个Python版的Workflow,让Python用户也能享受Workflow带来的绝佳体验。

jmespath.rs Python binding

rjmespath-py jmespath.rs Python binding.

Tindicators is a Python library to calculate the values of various technical indicators

Tindicators is a Python library to calculate the values of various technical indicators

Flames Calculater App used to calculate flames status between two names created using python's Flask web framework.
Flames Calculater App used to calculate flames status between two names created using python's Flask web framework.

Flames Finder Web App Flames Calculater App used to calculate flames status between two names created using python's Flask web framework. First, App g

A program to calculate the are of a triangle. made with Python.
A program to calculate the are of a triangle. made with Python.

Area-Calculator What is Area-Calculator? Area-Calculator is a program to find out the area of a triangle easily. fully made with Python. Needed a pyth

Comments
  • configuration error: `project.license` must be valid exactly by one definition (2 matches found):

    configuration error: `project.license` must be valid exactly by one definition (2 matches found):

    Hi ! By installing the package to install bancho.py, I've encountered a problem with the pkg.

    Collecting peace-performance-python==1.1.2
      Downloading peace-performance-python-1.1.2.tar.gz (25 kB)
      Installing build dependencies ... done
      Getting requirements to build wheel ... error
      error: subprocess-exited-with-error
      
      × Getting requirements to build wheel did not run successfully.
      │ exit code: 1
      ╰─> [80 lines of output]
          configuration error: `project.license` must be valid exactly by one definition (2 matches found):
          
              - keys:
                  'file': {type: string}
                required: ['file']
              - keys:
                  'text': {type: string}
                required: ['text']
          
          DESCRIPTION:
              `Project license <https://www.python.org/dev/peps/pep-0621/#license>`_.
          
          GIVEN VALUE:
              "MIT"
          
          OFFENDING RULE: 'oneOf'
          
          DEFINITION:
              {
                  "oneOf": [
                      {
                          "properties": {
                              "file": {
                                  "type": "string",
                                  "$$description": [
                                      "Relative path to the file (UTF-8) which contains the license for the",
                                      "project."
                                  ]
                              }
                          },
                          "required": [
                              "file"
                          ]
                      },
                      {
                          "properties": {
                              "text": {
                                  "type": "string",
                                  "$$description": [
                                      "The license of the project whose meaning is that of the",
                                      "`License field from the core metadata",
                                      "<https://packaging.python.org/specifications/core-metadata/#license>`_."
                                  ]
                              }
                          },
                          "required": [
                              "text"
                          ]
                      }
                  ]
              }
          Traceback (most recent call last):
            File "/usr/local/lib/python3.9/dist-packages/pip/_vendor/pep517/in_process/_in_process.py", line 363, in <module>
              main()
            File "/usr/local/lib/python3.9/dist-packages/pip/_vendor/pep517/in_process/_in_process.py", line 345, in main
              json_out['return_val'] = hook(**hook_input['kwargs'])
            File "/usr/local/lib/python3.9/dist-packages/pip/_vendor/pep517/in_process/_in_process.py", line 130, in get_requires_for_build_wheel
              return hook(config_settings)
            File "/usr/local/lib/python3.9/dist-packages/setuptools/build_meta.py", line 177, in get_requires_for_build_wheel
              return self._get_build_requires(
            File "/usr/local/lib/python3.9/dist-packages/setuptools/build_meta.py", line 159, in _get_build_requires
              self.run_setup()
            File "/usr/local/lib/python3.9/dist-packages/setuptools/build_meta.py", line 281, in run_setup
              super(_BuildMetaLegacyBackend,
            File "/usr/local/lib/python3.9/dist-packages/setuptools/build_meta.py", line 174, in run_setup
              exec(code, locals())
            File "<string>", line 20, in <module>
            File "/usr/local/lib/python3.9/dist-packages/setuptools/__init__.py", line 87, in setup
              return distutils.core.setup(**attrs)
            File "/usr/local/lib/python3.9/dist-packages/setuptools/_distutils/core.py", line 151, in setup
              dist.parse_config_files()
            File "/usr/local/lib/python3.9/dist-packages/setuptools/dist.py", line 868, in parse_config_files
              pyprojecttoml.apply_configuration(self, filename, ignore_option_errors)
            File "/usr/local/lib/python3.9/dist-packages/setuptools/config/pyprojecttoml.py", line 58, in apply_configuration
              config = read_configuration(filepath, True, ignore_option_errors, dist)
            File "/usr/local/lib/python3.9/dist-packages/setuptools/config/pyprojecttoml.py", line 122, in read_configuration
              validate(subset, filepath)
            File "/usr/local/lib/python3.9/dist-packages/setuptools/config/pyprojecttoml.py", line 47, in validate
              raise error from None
          ValueError: invalid pyproject.toml config: `project.license`
          [end of output]
      
      note: This error originates from a subprocess, and is likely not a problem with pip.
    error: subprocess-exited-with-error
    
    × Getting requirements to build wheel did not run successfully.
    │ exit code: 1
    ╰─> See above for output.
    
    note: This error originates from a subprocess, and is likely not a problem with pip.
    

    Got this error on a clean install (Ubuntu 22) & by following the steps of bancho.py installation. I didn't have this problem on x86 but since I moved to an aarch64 (ARM), it happened.

    opened by Lxmune 1
Releases(release-v2.0.0)
Owner
纯和平
Zues Auto Claimer Leaked By bazooka#0001

Zues Auto Claimer Leaked By bazooka#0001 put proxies in prox.txt put ssid in sid.txt put all users you want to target in user.txt for the login just t

1 Jan 15, 2022
TickerRain is an open-source web app that stores and analysis Reddit posts in a transparent and semi-interactive manner.

TickerRain is an open-source web app that stores and analysis Reddit posts in a transparent and semi-interactive manner

GonVas 180 Oct 08, 2022
Get the stats of a (or more) Hypixel player(s)

Hypixel_Stats Get the statistics of a (or more) Hypixel player(s) Who needs this? Everyone who plays a lot of Minecraft and often plays on mc.hypixel.

Finnomator 1 Feb 12, 2022
An kind of operating system portal to a variety of apps with pure python

pyos An kind of operating system portal to a variety of apps. Installation Run this on your terminal: git clone https://github.com/arjunj132/pyos.git

1 Jan 22, 2022
BridgeWalk is a partially-observed reinforcement learning environment with dynamics of varying stochasticity.

BridgeWalk is a partially-observed reinforcement learning environment with dynamics of varying stochasticity. The player needs to walk along a bridge to reach a goal location. When the player walks o

Danijar Hafner 6 Jun 13, 2022
Simple Wayland HotKey Daemon

swhkd Simple Wayland HotKey Daemon This project is still very new and I'm making new decisions everyday as to where I should drive this project. I'm u

Aakash Sen Sharma 407 Dec 30, 2022
This tool for beginner and help those people they gather information about Email Header Analysis, Instagram Information, Instagram Username Check, Ip Information, Phone Number Information, Port Scan

This tool for beginner and help those people they gather information about Email Header Analysis, Instagram Information, Instagram Username Check, Ip Information, Phone Number Information, Port Scan.

cb-kali 5 Feb 18, 2022
Xbox-Flood is for flood anything

Intruduction Installation Usage Installing Python 3 Wiki Getting Started Creating a Key Intruduction Xbox-Flood is for flooding messages (invitations

kayake 4 Feb 18, 2022
script buat mengcrack

setan script buat mengcrack cara install $ pkg install upgrade && pkg update $ pkg install python $ pkg install git $ pip install requests $ pip insta

1 Nov 03, 2021
Hydralit package is a wrapping and template project to combine multiple independant Streamlit applications into a multi-page application.

Hydralit The Hydralit package is a wrapping and template project to combine multiple independant (or somewhat dependant) Streamlit applications into a

Jackson Storm 108 Jan 08, 2023
This Python library searches through a static directory and appends artist, title, track number, album title, duration, and genre to a .json object

This Python library searches through a static directory (needs to match your environment) and appends artist, title, track number, album title, duration, and genre to a .json object. This .json objec

Edan Ybarra 1 Jun 20, 2022
A C-like hardware description language (HDL) adding high level synthesis(HLS)-like automatic pipelining as a language construct/compiler feature.

██████╗ ██╗██████╗ ███████╗██╗ ██╗███╗ ██╗███████╗ ██████╗ ██╔══██╗██║██╔══██╗██╔════╝██║ ██║████╗ ██║██╔════╝██╔════╝ ██████╔╝██║██████╔╝█

Julian Kemmerer 391 Jan 01, 2023
A class to draw curves expressed as L-System production rules

A class to draw curves expressed as L-System production rules

Juna Salviati 6 Sep 09, 2022
MIB2 STD ZR Firmware Upgrade

Upgrade MIB2 STD ZR Firmware (without Navigation) About This repository contains some scripts and documentation how to upgrade the MIB2 firmware to a

Fabian 18 Dec 29, 2022
High-level bindings to the Valhalla framework.

Valhalla for Python This spin-off project simply offers improved Python bindings to the fantastic Valhalla project. Installation pip install valhalla

GIS • OPS 20 Dec 13, 2022
flake8 plugin which checks that there is no use of sleep in the code.

flake8-sleep flake8 plugin which checks for use of sleep function. installation Using Pypi: pip install flake8-sleep flake8 codes Code Description SLP

1 Nov 26, 2021
A simple spyware in python.

Spyware-Python- Dependencies: Python 3.x OpenCV PyAutoGUI PyMongo (for mongodb connection) Flask (Web Server) Ngrok (helps us push our fla

Abubakar 3 Sep 07, 2022
Distributed behavioral experiments

Autopilot Docs Paper Forum Hardware Autopilot is a Python framework for performing complex, hardware-intensive behavioral experiments with swarms of n

70 Dec 14, 2022
OpenTable Reservation Maker For Python

OpenTable-Reservation-Maker The code that corresponds with this blog post on writing a script to make reservations for me on opentable Getting started

JonLuca De Caro 36 Nov 10, 2022
"Hacking" the (Telekom) Zyxel GPON SFP module (PMG3000-D20B)

"Hacking" the (Telekom) Zyxel GPON SFP module (PMG3000-D20B) The SFP can be sour

Matthias Riegler 52 Jan 03, 2023