Skip to main content

Lightweight, dependency-free Python implementation of LexoRank algorithm for fractional indexing

Project description

LexoRank Python工具库

lexorank-py是用于分数索引的lexorank算法的轻量级、无依赖性的Python实现,实现了高效的拖放排序、动态列表重新排序和插入任何位置的操作,而无需完全重新平衡列表。 非常适合构建可排序的任务列表、看板、脚本编辑器或任何需要持久、稳定排序键的UI。

目录结构

py-lexorank/
├── src/py_lexorank/              # Python import 包:py_lexorank
│   ├── __init__.py
│   ├── lexorank_key.py           # 业务层 API(推荐使用)
│   └── lexorank/                 # LexoRank 核心实现(算法层)
│       ├── __init__.py
│       ├── __main__.py           # CLI:python -m py_lexorank.lexorank ...
│       ├── lexo_decimal.py
│       ├── lexo_integer.py
│       ├── lexo_rank.py
│       ├── lexo_rank_bucket.py
│       └── numeral_systems.py
├── examples/                     # 示例/造排序数据脚本(不随 pip 包发布)
│   └── demo.py
├── tests/                        # 单元测试
│   └── test_lexorank.py
├── pyproject.toml
└── README.md

项目概述

LexoRank 是一种排序算法,允许在列表中任意位置插入新元素而无需重新排列整个列表。它通过在两个已存在的排序键之间生成新的排序键来实现这一点。

核心概念

  • 排序键(Rank Key):用于数据库排序的字符串,按字典序排序即可得到正确的顺序
  • 分数索引(Fractional Indexing):在两个排序键之间生成新键的技术
  • 分桶(Bucket):用于隔离不同分组的排序空间,避免 rank 过度变长
  • 进制系统:使用 base36 进制系统进行数值表示

使用方法

基础安装和使用

安装

使用 pip 安装:

pip install py-lexorank

或使用 uv (更快的包管理器):

uv pip install py-lexorank

推荐直接导入 LexoRankKey 类即可开始使用:

from py_lexorank import LexoRankKey

# 初始化空列表的第一条记录
first_rank = LexoRankKey.init_for_empty_list()

# 在两条记录之间插入
second_rank = LexoRankKey.insert_after(first_rank)
middle_rank = LexoRankKey.insert_between(first_rank, second_rank)

# 插入到最前面
before_first = LexoRankKey.insert_before(first_rank)

# 通用插入接口
new_rank = LexoRankKey.insert(prev_rank, next_rank)

常见使用场景

1. 空列表插入第一条记录

# 当列表为空时,插入第一条记录
first_rank = LexoRankKey.init_for_empty_list()

2. 追加到列表末尾

# 在现有列表末尾追加新记录
new_rank = LexoRankKey.insert_after(last_rank)

3. 在两条记录之间插入

# 在两个已知记录之间插入新记录(常用:拖拽排序)
new_rank = LexoRankKey.insert_between(left_rank, right_rank)

4. 插入到列表开头

# 在列表开头插入新记录
new_rank = LexoRankKey.insert_before(first_rank)

5. 通用插入接口

# 最灵活的插入方式,适用于所有场景
new_rank = LexoRankKey.insert(prev_rank, next_rank)

命令行工具

LexoRank 提供了命令行工具用于开发和调试:

# 方式1:安装后直接使用脚本命令(推荐)
py-lexorank middle

# 方式2:使用 python -m 方式调用
# 获取最小 rank
python -m py_lexorank.lexorank min

# 获取中间 rank
python -m py_lexorank.lexorank middle

# 获取最大 rank
python -m py_lexorank.lexorank max

# 获取指定 rank 的下一个 rank
python -m py_lexorank.lexorank next "0|0i0000:"

# 获取指定 rank 的上一个 rank
python -m py_lexorank.lexorank prev "0|0i0000:"

# 在两个 rank 之间生成新的 rank
python -m py_lexorank.lexorank between "0|000000:" "0|zzzzzz:"

演示脚本

运行演示脚本来查看各种使用场景:

  1. 直接运行(默认空列表自动插入第一条)
PYTHONPATH=src python examples/demo.py
  1. 指定批量生成数量(默认空列表自动插入第一条,根据生成的第一条一次生成 X 个递增 rank)
PYTHONPATH=src python examples/demo.py --count 20
  1. 指定起始 rank(从某个已有 rank 后面开始批量生成X 个递增 rank) 注意:rank 里有 |,在 zsh 里必须用引号包起来
PYTHONPATH=src python examples/demo.py --start '0|hzzzzz:' --count 10

测试

在仓库根目录运行:

PYTHONPATH=src python -m unittest discover -s tests -v

文件详细说明

源码位于 src/py_lexorank/

  • src/py_lexorank/lexorank_key.py:业务层 API(字符串进出,推荐)
  • src/py_lexorank/lexorank/:LexoRank 算法核心实现与 CLI
  • examples/demo.py:示例/造排序数据脚本(repo-only)
  • tests/test_lexorank.py:单元测试

业务场景应用

1. 任务列表排序

在项目管理应用中,用户经常需要调整任务的顺序。使用 LexoRank 可以避免每次重排都更新整个列表:

from py_lexorank.lexorank_key import LexoRankKey

# 创建新任务并插入到列表中
def add_task_after(task_list, target_task_id):
    target_task = get_task(target_task_id)
    next_task = get_next_task(target_task_id)
    
    new_rank = LexoRankKey.insert_between(target_task.rank, next_task.rank)
    create_task(rank=new_rank)

2. 菜单项排序

在菜单编辑器中,用户可以通过拖拽调整菜单项的顺序:

from lexorank_key import LexoRankKey

# 拖拽排序:将项目从 old_pos 移动到 new_pos
def move_menu_item(item_id, old_pos, new_pos):
    if new_pos == 0:  # 移到开头
        new_rank = LexoRankKey.insert_before(get_first_item().rank)
    elif new_pos == get_last_position():  # 移到末尾
        new_rank = LexoRankKey.insert_after(get_last_item().rank)
    else:  # 移到中间
        prev_item = get_previous_item(new_pos)
        next_item = get_next_item(new_pos)
        new_rank = LexoRankKey.insert_between(prev_item.rank, next_item.rank)
    
    update_item_rank(item_id, new_rank)

3. 场景排序

在视频制作应用中,用户可以对场景进行排序:

from lexorank_key import LexoRankKey

def reorder_scenes(scene_ids, new_order):
    """根据新顺序重新排列场景"""
    ordered_scenes = []
    for i, scene_id in enumerate(new_order):
        if i == 0:
            # 第一个场景使用初始 rank 或者基于第一个现有场景的 rank
            if len(ordered_scenes) > 0:
                rank = LexoRankKey.insert_before(ordered_scenes[0].rank)
            else:
                rank = LexoRankKey.init_for_empty_list()
        else:
            # 后续场景插入到前一个场景之后
            rank = LexoRankKey.insert_after(ordered_scenes[-1].rank)
        
        ordered_scenes.append(Scene(id=scene_id, rank=rank))
    
    # 批量更新所有场景的 rank
    bulk_update_scene_ranks(ordered_scenes)

注意事项

并发安全

当多个请求并发向同一缝隙插入时,可能会生成重复的 rank。建议:

  1. 在数据库中设置唯一约束
  2. 在业务层添加适当的锁或重试机制
  3. 处理插入冲突的情况

性能考虑

  • LexoRank 字符串会随着频繁的插入操作逐渐变长
  • 当 rank 字符串变得过长时,可能需要执行重新编号操作
  • 对于大量数据的排序,定期进行碎片整理是有益的

测试

运行单元测试验证功能:

python -m lexorank.test_lexorank

或直接运行测试文件:

python lexorank/test_lexorank.py

许可证

本项目遵循 MIT 许可证。

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

py_lexorank-1.0.1.tar.gz (24.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

py_lexorank-1.0.1-py3-none-any.whl (21.9 kB view details)

Uploaded Python 3

File details

Details for the file py_lexorank-1.0.1.tar.gz.

File metadata

  • Download URL: py_lexorank-1.0.1.tar.gz
  • Upload date:
  • Size: 24.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.2

File hashes

Hashes for py_lexorank-1.0.1.tar.gz
Algorithm Hash digest
SHA256 cd351eefa30356157e8ff4cc51c6737f5818306250ca763075f30428665e7a7d
MD5 18158b638225f996cdd99f816a8531a5
BLAKE2b-256 4eeefb2b64ca54365d0b15185f5ac9375cbf866e91c52b0964b01180aaf57ed0

See more details on using hashes here.

File details

Details for the file py_lexorank-1.0.1-py3-none-any.whl.

File metadata

  • Download URL: py_lexorank-1.0.1-py3-none-any.whl
  • Upload date:
  • Size: 21.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.2

File hashes

Hashes for py_lexorank-1.0.1-py3-none-any.whl
Algorithm Hash digest
SHA256 3aacae94c46246c8cb04ad3b04b77fc230a448da507fa78151e7878d015ebdc3
MD5 baab466a877016483ca0d3150a34199b
BLAKE2b-256 16ffc23745ded63bd742f6118d468e50fb23a9332008cf5a2f668acc33a57dfe

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page