rust-pyfunc 0.76.9__tar.gz → 0.76.14__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/.github/workflows/CI.yml +4 -1
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/.gitignore +5 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/Cargo.lock +1 -1
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/Cargo.toml +6 -2
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/PKG-INFO +1 -1
- rust_pyfunc-0.76.14/README.md +33 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/alter.sh +3 -2
- rust_pyfunc-0.76.14/freeze_version.sh +210 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/__init__.py +1 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/__init__.pyi +2 -0
- rust_pyfunc-0.76.14/python/rust_pyfunc/factor_task.py +191 -0
- rust_pyfunc-0.76.14/python/rust_pyfunc/factor_taskd.py +560 -0
- rust_pyfunc-0.76.14/python/rust_pyfunc/minute_data_reader.py +48 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/parallel_computing.pyi +2 -1
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/trading_data_utils.py +12 -2
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/trading_day.py +29 -5
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_pair_metrics.rs +9 -5
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/parallel_computing.rs +184 -21
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/parallel_computing_date_only.rs +191 -236
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/personalized_meeting_features.rs +10 -7
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/simple_parallel.rs +25 -31
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/tail_v4_pipeline.rs +477 -92
- rust_pyfunc-0.76.9/AGENTS.md +0 -108
- rust_pyfunc-0.76.9/CLAUDE.md +0 -131
- rust_pyfunc-0.76.9/CRUSH.md +0 -40
- rust_pyfunc-0.76.9/README.md +0 -770
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/.factory/settings.json +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/.github/workflows/deploy.yml +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/FACTOR_NEUTRALIZATION_REQUIREMENTS.md +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/agents/skills/agent-trading-builder/SKILL.md +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/PriceTree.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/PriceTreeViz.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/RollingFutureAccessor.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/TRADE_PEAK_ANALYSIS_README.md +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/brachistochrone_curve.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/calculate_shannon_entropy_change.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/calculate_shannon_entropy_change_at_low.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/compute_max_eigenvalue.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/dct_basis_functions.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/dct_path_patterns.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/dct_reconstruction.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/dct_visualization.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/dtw_distance.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/find_follow_volume_sum_same_price.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/find_follow_volume_sum_same_price_and_flag.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/find_half_energy_time.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/find_local_peaks_within_window.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/find_max_range_product.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/identify_segments.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/index.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/jaccard_similarity.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/mark_follow_groups.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/mark_follow_groups_with_flag.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/max_range_loop.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/min_range_loop.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/min_word_edit_distance.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/ols.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/ols_predict.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/ols_residuals.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/parallel_computing_system.md +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/rolling_cv.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/rolling_qcv.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/rolling_volatility.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/rolling_window_stat.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/search_data.json +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/static/search.js +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/static/style.css +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/sum_as_string.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/transfer_entropy.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/trend.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/trend_fast.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/vectorize_sentences.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs/vectorize_sentences_list.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs//344/275/277/347/224/250/350/257/264/346/230/216.md" +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs//345/256/214/346/210/220/346/200/273/347/273/223.md" +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/docs_generator.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/ds_plan_true.md +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/hmm_visualizer.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/pyproject.toml +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/abm_analysis.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/agent_simulator.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/agent_trading_daily.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/agent_trading_daily.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/copula.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/core_functions.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/pandas_correlation.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/pandas_correlation.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/pandas_corrwith.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/pandas_extensions.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/pandas_merge.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/pandas_rank.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/rolling_future.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/rolling_past.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/statistical_analysis.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/text_analysis.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/theme_cluster_factors.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/theme_feature_expansion.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/theme_feature_expansion_data.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/theme_feature_expansion_data.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/time_series.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/trading_analysis.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/trading_data_utils.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/tree_structures.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/treevisual.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/web_manager.py +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/python/rust_pyfunc/web_manager.pyi +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/rust-toolchain.toml +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/abnormal_asks_analyzer.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/acceleration_follow_agent.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/bottom_fishing_agent.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/buy_ratio_agent.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/exhaustion_reversal_agent.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/follow_flow_agent.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/momentum_agent.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/py_bindings.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/simulator.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/trait_def.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/types.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_simulator/utils.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_trading_features/core.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_trading_features/metrics.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_trading_features/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_trading_features/py_bindings.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/agent_trading_features/types.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/allo_microstructure.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/allo_microstructure_v2.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/allo_microstructure_v3.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/backup_column_cache.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/backup_reader.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/backup_writer.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/column_correlation.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/copula.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/corr_diff_features.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/dct_transform.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/difference_matrix.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/effective_memory_length.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/entropy_analysis.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/error/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/factor_neutralization_io_optimized.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/frontier_dist.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/ghost_market_maker.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/gp_correlation_dimension.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/grouping.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/hawkes_advisor.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/hawkes_analysis.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/illusion_liquidity_distance.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/integer_small_peak_features.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lagged_regression.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lagged_regression_incremental.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lagged_regression_optimized.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lagged_regression_simd.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lib.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/limit_order_lifecycle.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/limit_order_lifecycle_v2.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/long_order_analysis.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lz_complexity.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/lz_complexity_detailed.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/market_correlation.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/microstructure_pattern_features.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/microstructure_pattern_features_optimized.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/microstructure_pattern_features_v2.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/mutual_information.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/mutual_information_2d.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/mutual_information_2d_final.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/mutual_information_2d_fixed.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_contamination.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_neighborhood.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_price_statistics.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_price_statistics_bucketed.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_price_statistics_order_level.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_records_ultra_sorted.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_records_ultra_sorted_bucketed.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_records_ultra_sorted_v2_optimized.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/order_records_ultra_sorted_v3.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/orderbook_volume_cov_factors.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/pandas_ext/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/passive_order_features.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/permutation_analysis_v0816_fixed.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/price_breakthrough_stats.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/price_cycle_b_segments_enhanced.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/safe_eigenvalue.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/sequence/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/series_rank.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/skewness.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/eigenvalue_analysis.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/eigenvalue_analysis_modified.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/fast_correlation.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/fast_correlation_v2.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/hmm_trend_prediction.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/local_correlation.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/rolling_correlation_mean.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/rolling_window_core_feature.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/rolling_window_core_feature_optimized.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/rolling_window_core_feature_simd.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/statistics/rolling_window_core_feature_ultra.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/tail_v2_backtest_block.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/tail_v2_block_neutralizer.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/tail_v2_ic_corr_filter.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/tail_v2_rank_roll_factor.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/text/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/text/string_proximity.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/theme_cluster_factors.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/theme_cluster_factors_batch.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/theme_feature_expansion.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_irreversibility.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/fast_extreme.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/lyapunov.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/retreat_advance.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/retreat_advance_v2.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/super_extreme.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/time_series/trend_mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/topk_corr_matrix.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/trade_analysis_ultra_turbo.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/trade_peak_analysis.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/trade_records_ultra_sorted.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/tree/mod.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/vector_similarity.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/src/vector_similarity_optimized.rs +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/templates/base.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/templates/function.html +0 -0
- {rust_pyfunc-0.76.9 → rust_pyfunc-0.76.14}/templates/index.html +0 -0
|
@@ -40,8 +40,9 @@ jobs:
|
|
|
40
40
|
uses: PyO3/maturin-action@v1
|
|
41
41
|
with:
|
|
42
42
|
target: ${{ matrix.platform.target }}
|
|
43
|
-
args: --release --out dist --find-interpreter
|
|
43
|
+
args: --release --out dist --find-interpreter --no-default-features
|
|
44
44
|
sccache: 'true'
|
|
45
|
+
before-script-windows: choco install cmake
|
|
45
46
|
manylinux: auto
|
|
46
47
|
before-script-linux: ${{ matrix.platform.target == 'aarch64' && 'pip install cmake' || '' }}
|
|
47
48
|
- name: Upload wheels
|
|
@@ -179,6 +180,8 @@ jobs:
|
|
|
179
180
|
- uses: actions/setup-python@v5
|
|
180
181
|
with:
|
|
181
182
|
python-version: '3.9'
|
|
183
|
+
- name: Install dependencies
|
|
184
|
+
run: pip install pandas numpy
|
|
182
185
|
- name: Install rust_pyfunc
|
|
183
186
|
run: pip install rust_pyfunc --no-index --find-links dist
|
|
184
187
|
- name: Test import
|
|
@@ -197,6 +197,9 @@ Thumbs.db
|
|
|
197
197
|
.windsurf/
|
|
198
198
|
.crush/
|
|
199
199
|
AGENT.md
|
|
200
|
+
CLAUDE.md
|
|
201
|
+
AGENTS.md
|
|
202
|
+
CRUSH.md
|
|
200
203
|
|
|
201
204
|
# Logs
|
|
202
205
|
*.log
|
|
@@ -234,3 +237,5 @@ docs/theme_feature_expansion_explanation.md
|
|
|
234
237
|
.vtcode/skills/INDEX.md
|
|
235
238
|
.vtcode/terminals/INDEX.md
|
|
236
239
|
.mindfs/sessions/session-list.db
|
|
240
|
+
.maturin_zig/*
|
|
241
|
+
dist_versions/*
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[package]
|
|
2
2
|
name = "rust_pyfunc"
|
|
3
|
-
version = "0.76.
|
|
3
|
+
version = "0.76.14"
|
|
4
4
|
edition = "2021"
|
|
5
5
|
description = "A collection of high-performance Python functions implemented in Rust"
|
|
6
6
|
readme = "README.md"
|
|
@@ -46,8 +46,12 @@ log = "0.4"
|
|
|
46
46
|
once_cell = "1.19"
|
|
47
47
|
csv = "1.3"
|
|
48
48
|
ndarray-npy = "0.8"
|
|
49
|
-
hdf5-metno = { version = "0.12", features = ["static", "zlib"] }
|
|
49
|
+
hdf5-metno = { version = "0.12", features = ["static", "zlib"], optional = true }
|
|
50
50
|
zstd = "0.13"
|
|
51
|
+
|
|
52
|
+
[features]
|
|
53
|
+
default = ["hdf5"]
|
|
54
|
+
hdf5 = ["hdf5-metno"]
|
|
51
55
|
# Unix-specific dependencies for fork mode
|
|
52
56
|
[target.'cfg(unix)'.dependencies]
|
|
53
57
|
nix = { version = "0.27", features = ["process", "signal", "fs"] }
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# rust_pyfunc
|
|
2
|
+
|
|
3
|
+
用 Rust 写的高性能 Python 库。专治各种计算密集场景:金融数据分析、时间序列处理、统计计算——Python 搞不定的性能问题,这里管。
|
|
4
|
+
|
|
5
|
+
## 安装
|
|
6
|
+
|
|
7
|
+
```shell
|
|
8
|
+
pip install rust_pyfunc
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## 使用
|
|
12
|
+
|
|
13
|
+
```python
|
|
14
|
+
import rust_pyfunc as rp
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
## 开发
|
|
18
|
+
|
|
19
|
+
```bash
|
|
20
|
+
pip install maturin
|
|
21
|
+
maturin develop --release
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
## 项目结构
|
|
25
|
+
|
|
26
|
+
```
|
|
27
|
+
src/ # Rust 源码
|
|
28
|
+
python/ # Python 包 & 类型提示
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
## License
|
|
32
|
+
|
|
33
|
+
MIT
|
|
@@ -22,8 +22,9 @@ conda activate chenzongwei311
|
|
|
22
22
|
# 3. 切换到你的项目目录 (如果当前目录不是)
|
|
23
23
|
# cd /path/to/your/maturin/project
|
|
24
24
|
|
|
25
|
-
# 4. 运行 maturin develop
|
|
26
|
-
|
|
25
|
+
# 4. 运行 maturin develop (使用 mold 链接器 + sccache 编译缓存加速)
|
|
26
|
+
export PATH="/home/chenzongwei/.local/bin:$PATH"
|
|
27
|
+
/home/chenzongwei/.local/bin/mold -run maturin develop --release
|
|
27
28
|
|
|
28
29
|
# 如果需要,你也可以在脚本结束时停用环境
|
|
29
30
|
# conda deactivate
|
|
@@ -0,0 +1,210 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
# freeze_version.sh — 将当前项目打包为版本锁定的独立 wheel
|
|
3
|
+
#
|
|
4
|
+
# 用法:
|
|
5
|
+
# ./freeze_version.sh # 从 Cargo.toml 自动读取版本号
|
|
6
|
+
# ./freeze_version.sh 0_76_8 # 手动指定版本标签
|
|
7
|
+
# ./freeze_version.sh --manylinux2014 # 构建 glibc 2.17+ 兼容 wheel
|
|
8
|
+
# ./freeze_version.sh 0_76_8 --manylinux_2_31 # 构建 glibc 2.31+ 兼容 wheel
|
|
9
|
+
#
|
|
10
|
+
# 输出:
|
|
11
|
+
# dist_versions/rust_pyfunc_<version>-<ver>-cp*-cp*-linux_x86_64.whl
|
|
12
|
+
# 加上 --manylinux* 参数后:
|
|
13
|
+
# dist_versions/rust_pyfunc_<version>-<ver>-cp*-cp*-manylinux_*_x86_64.whl
|
|
14
|
+
#
|
|
15
|
+
# 安装后使用:
|
|
16
|
+
# import rust_pyfunc_0_76_8 as rp
|
|
17
|
+
|
|
18
|
+
set -euo pipefail
|
|
19
|
+
|
|
20
|
+
PROJECT_DIR="$(cd "$(dirname "$0")" && pwd)"
|
|
21
|
+
cd "$PROJECT_DIR"
|
|
22
|
+
|
|
23
|
+
# ── 0. 确保 zig 可用(用于 --manylinux* 交叉链接)─────────────
|
|
24
|
+
ZIG_BIN="$(python3 -c 'import ziglang, os; print(os.path.join(os.path.dirname(ziglang.__file__), "zig"))' 2>/dev/null || true)"
|
|
25
|
+
ZIG_DIR="${PROJECT_DIR}/.maturin_zig"
|
|
26
|
+
if [ -n "$ZIG_BIN" ] && [ -x "$ZIG_BIN" ]; then
|
|
27
|
+
mkdir -p "${ZIG_DIR}/bin"
|
|
28
|
+
ln -sf "$ZIG_BIN" "${ZIG_DIR}/bin/zig"
|
|
29
|
+
# 创建 cargo 包装器:把 cargo → cargo-zigbuild
|
|
30
|
+
# 注意:
|
|
31
|
+
# - CARGO_BUILD_TARGET 在包装器内部设置,这样 maturin 读不到带后缀的 triple
|
|
32
|
+
# - CARGO 指向真正的 cargo,避免 cargo-zigbuild 子调用又回到包装器形成死循环
|
|
33
|
+
CARGO_ZIGBUILD="/home/chenzongwei/.conda/envs/chenzongwei311/bin/cargo-zigbuild"
|
|
34
|
+
REAL_CARGO="$(command -v cargo)"
|
|
35
|
+
cat > "${ZIG_DIR}/bin/cargo" << CARGO_WRAPPER
|
|
36
|
+
#!/bin/bash
|
|
37
|
+
export CARGO_BUILD_TARGET="x86_64-unknown-linux-gnu.2.31"
|
|
38
|
+
export CARGO="${REAL_CARGO}"
|
|
39
|
+
exec ${CARGO_ZIGBUILD} "\$@"
|
|
40
|
+
CARGO_WRAPPER
|
|
41
|
+
chmod +x "${ZIG_DIR}/bin/cargo"
|
|
42
|
+
fi
|
|
43
|
+
|
|
44
|
+
# ── 1. 确定版本标签与兼容性参数 ────────────────────────────────
|
|
45
|
+
VERSION_TAG=""
|
|
46
|
+
COMPAT_TAG=""
|
|
47
|
+
|
|
48
|
+
for arg in "$@"; do
|
|
49
|
+
case "$arg" in
|
|
50
|
+
--manylinux*)
|
|
51
|
+
COMPAT_TAG="${arg#--}"
|
|
52
|
+
;;
|
|
53
|
+
*)
|
|
54
|
+
VERSION_TAG="$arg"
|
|
55
|
+
;;
|
|
56
|
+
esac
|
|
57
|
+
done
|
|
58
|
+
|
|
59
|
+
if [ -z "$VERSION_TAG" ]; then
|
|
60
|
+
VERSION_TAG=$(grep '^version = ' Cargo.toml | head -1 | sed 's/.*"\(.*\)".*/\1/' | tr '.' '_')
|
|
61
|
+
fi
|
|
62
|
+
|
|
63
|
+
PACKAGE_NAME="rust_pyfunc_${VERSION_TAG}"
|
|
64
|
+
TMPDIR="/tmp/build_${PACKAGE_NAME}_$$"
|
|
65
|
+
OUTPUT_DIR="${PROJECT_DIR}/dist_versions"
|
|
66
|
+
PYTHON_SRC="${PROJECT_DIR}/python/rust_pyfunc"
|
|
67
|
+
|
|
68
|
+
echo "========================================"
|
|
69
|
+
echo " 打包版本: ${PACKAGE_NAME}"
|
|
70
|
+
echo " 兼容目标: ${COMPAT_TAG:-系统原生 (glibc $(ldd --version 2>&1 | head -1 | grep -oP '\d+\.\d+$'))}"
|
|
71
|
+
echo " 临时目录: ${TMPDIR}"
|
|
72
|
+
echo " 输出目录: ${OUTPUT_DIR}"
|
|
73
|
+
echo "========================================"
|
|
74
|
+
|
|
75
|
+
# ── 2. 创建临时构建目录 ────────────────────────────────────────
|
|
76
|
+
rm -rf "$TMPDIR"
|
|
77
|
+
mkdir -p "$TMPDIR"
|
|
78
|
+
|
|
79
|
+
# ── 3. 复制 Python 源码,并重命名包目录 ────────────────────────
|
|
80
|
+
cp -r "$PYTHON_SRC" "${TMPDIR}/${PACKAGE_NAME}"
|
|
81
|
+
|
|
82
|
+
# ── 4. 修补 import 语句(绝对自导入 → 相对导入) ────────────────
|
|
83
|
+
# 这些文件用了 from rust_pyfunc.xxx import yyy(绝对导入),
|
|
84
|
+
# 包名改成 rust_pyfunc_0_76_8 后必须改为相对导入 from .xxx import yyy
|
|
85
|
+
|
|
86
|
+
cd "${TMPDIR}/${PACKAGE_NAME}"
|
|
87
|
+
|
|
88
|
+
echo "[patch] __init__.py ..."
|
|
89
|
+
# __init__.py 第 3 行: from rust_pyfunc.rust_pyfunc import * → from .rust_pyfunc import *
|
|
90
|
+
sed -i 's/^from rust_pyfunc\.rust_pyfunc import \*/from .rust_pyfunc import */' __init__.py
|
|
91
|
+
# __init__.py 第 5 行: from rust_pyfunc import * → 删除(冗余)
|
|
92
|
+
sed -i '/^from rust_pyfunc import \*$/d' __init__.py
|
|
93
|
+
# __init__.py 第 6 行: from rust_pyfunc.rolling_future import ... → from .rolling_future import ...
|
|
94
|
+
sed -i 's/^from rust_pyfunc\.rolling_future import/from .rolling_future import/' __init__.py
|
|
95
|
+
# __init__.py 第 7 行: from rust_pyfunc.rolling_past import ... → from .rolling_past import ...
|
|
96
|
+
sed -i 's/^from rust_pyfunc\.rolling_past import/from .rolling_past import/' __init__.py
|
|
97
|
+
|
|
98
|
+
echo "[patch] rolling_future.py ..."
|
|
99
|
+
sed -i 's/^from rust_pyfunc\.rust_pyfunc import/from .rust_pyfunc import/' rolling_future.py
|
|
100
|
+
|
|
101
|
+
echo "[patch] rolling_past.py ..."
|
|
102
|
+
sed -i 's/^from rust_pyfunc\.rust_pyfunc import/from .rust_pyfunc import/' rolling_past.py
|
|
103
|
+
|
|
104
|
+
echo "[patch] treevisual.py ..."
|
|
105
|
+
sed -i 's/^from rust_pyfunc\.rust_pyfunc import/from .rust_pyfunc import/' treevisual.py
|
|
106
|
+
|
|
107
|
+
echo "[patch] pandas_corrwith.py ..."
|
|
108
|
+
sed -i 's/^from rust_pyfunc\.rust_pyfunc import/from .rust_pyfunc import/' pandas_corrwith.py
|
|
109
|
+
|
|
110
|
+
# 确认修补结果
|
|
111
|
+
echo ""
|
|
112
|
+
echo "修补后的导入语句:"
|
|
113
|
+
grep -n '^from \.rust_pyfunc import' __init__.py rolling_future.py rolling_past.py treevisual.py pandas_corrwith.py 2>/dev/null || true
|
|
114
|
+
echo ""
|
|
115
|
+
|
|
116
|
+
# ── 5. 复制 Rust 源码 + 辅助文件 ────────────────────────────────
|
|
117
|
+
cp -r "${PROJECT_DIR}/src" "$TMPDIR/src"
|
|
118
|
+
cp "${PROJECT_DIR}/Cargo.toml" "$TMPDIR/Cargo.toml"
|
|
119
|
+
[ -f "${PROJECT_DIR}/Cargo.lock" ] && cp "${PROJECT_DIR}/Cargo.lock" "$TMPDIR/Cargo.lock" || true
|
|
120
|
+
[ -f "${PROJECT_DIR}/rust-toolchain.toml" ] && cp "${PROJECT_DIR}/rust-toolchain.toml" "$TMPDIR/" || true
|
|
121
|
+
cp "${PROJECT_DIR}/README.md" "$TMPDIR/README.md" 2>/dev/null || touch "$TMPDIR/README.md"
|
|
122
|
+
|
|
123
|
+
# ── 6. 创建临时的 pyproject.toml ──────────────────────────────
|
|
124
|
+
cat > "$TMPDIR/pyproject.toml" << PYPROJECT
|
|
125
|
+
[build-system]
|
|
126
|
+
requires = ["maturin>=1.3,<2.0"]
|
|
127
|
+
build-backend = "maturin"
|
|
128
|
+
|
|
129
|
+
[project]
|
|
130
|
+
name = "${PACKAGE_NAME}"
|
|
131
|
+
requires-python = ">=3.8"
|
|
132
|
+
dynamic = ["version"]
|
|
133
|
+
|
|
134
|
+
[tool.maturin]
|
|
135
|
+
features = ["pyo3/extension-module"]
|
|
136
|
+
python-source = "."
|
|
137
|
+
module-name = "${PACKAGE_NAME}.rust_pyfunc"
|
|
138
|
+
PYPROJECT
|
|
139
|
+
|
|
140
|
+
echo "pyproject.toml:"
|
|
141
|
+
cat "$TMPDIR/pyproject.toml"
|
|
142
|
+
echo ""
|
|
143
|
+
|
|
144
|
+
# ── 7. 构建 wheel ─────────────────────────────────────────────
|
|
145
|
+
|
|
146
|
+
build_for_python() {
|
|
147
|
+
local python_bin="$1"
|
|
148
|
+
local compat="$2"
|
|
149
|
+
local label="$3"
|
|
150
|
+
|
|
151
|
+
cd "$TMPDIR"
|
|
152
|
+
|
|
153
|
+
local opts="--release --interpreter $python_bin"
|
|
154
|
+
if [ -n "$compat" ]; then
|
|
155
|
+
opts="$opts --compatibility $compat --no-default-features"
|
|
156
|
+
fi
|
|
157
|
+
|
|
158
|
+
echo "━━━ 构建 [$label] ━━━"
|
|
159
|
+
echo "解释器: $($python_bin --version 2>&1)"
|
|
160
|
+
echo "选项: maturin build $opts"
|
|
161
|
+
echo ""
|
|
162
|
+
|
|
163
|
+
# 需要 zig 做交叉链接
|
|
164
|
+
if [ -n "$compat" ]; then
|
|
165
|
+
# 用 cargo-zigbuild 替代 cargo —— 自动用 zig 编译和链接,
|
|
166
|
+
# 产生目标 glibc 版本的二进制
|
|
167
|
+
export PATH="${ZIG_DIR}/bin:$PATH" # 内有 cargo 包装器(含 CARGO/CARGO_BUILD_TARGET 设置)
|
|
168
|
+
echo " [zig] 通过 cargo-zigbuild 构建 (glibc 2.31)"
|
|
169
|
+
fi
|
|
170
|
+
CARGO_TARGET_DIR="${PROJECT_DIR}/target" maturin build $opts 2>&1
|
|
171
|
+
|
|
172
|
+
echo ""
|
|
173
|
+
echo "[$label] 构建完成"
|
|
174
|
+
echo ""
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
# 第一次构建:当前 Python,遵循 --manylinux* 参数
|
|
178
|
+
CURRENT_PYTHON=$(command -v python3)
|
|
179
|
+
build_for_python "$CURRENT_PYTHON" "$COMPAT_TAG" "当前环境"
|
|
180
|
+
|
|
181
|
+
# 第二次构建:Python 3.9 + manylinux_2_31
|
|
182
|
+
PY39="/opt/anaconda3/bin/python3.9"
|
|
183
|
+
if [ -x "$PY39" ]; then
|
|
184
|
+
build_for_python "$PY39" "manylinux_2_31" "Python 3.9 + manylinux_2_31"
|
|
185
|
+
else
|
|
186
|
+
echo "[跳过] python3.9 未找到: ${PY39}"
|
|
187
|
+
fi
|
|
188
|
+
|
|
189
|
+
# ── 8. 收集产物 ────────────────────────────────────────────────
|
|
190
|
+
mkdir -p "$OUTPUT_DIR"
|
|
191
|
+
cp "${PROJECT_DIR}"/target/wheels/"${PACKAGE_NAME}"*.whl "$OUTPUT_DIR/"
|
|
192
|
+
|
|
193
|
+
# ── 9. 清理 ────────────────────────────────────────────────────
|
|
194
|
+
rm -rf "$TMPDIR"
|
|
195
|
+
|
|
196
|
+
# ── 10. 输出结果 ───────────────────────────────────────────────
|
|
197
|
+
echo ""
|
|
198
|
+
echo "========================================"
|
|
199
|
+
echo " ✅ 打包完成"
|
|
200
|
+
echo "========================================"
|
|
201
|
+
ls -lh "${OUTPUT_DIR}/${PACKAGE_NAME}"*.whl 2>/dev/null || echo "(wheel 文件未找到)"
|
|
202
|
+
|
|
203
|
+
echo ""
|
|
204
|
+
echo "安装命令:"
|
|
205
|
+
echo " pip install ${OUTPUT_DIR}/${PACKAGE_NAME}-*.whl"
|
|
206
|
+
echo ""
|
|
207
|
+
echo "使用方式:"
|
|
208
|
+
echo " import ${PACKAGE_NAME} as rp"
|
|
209
|
+
echo " rp.fast_rank(...)"
|
|
210
|
+
echo ""
|
|
@@ -34,6 +34,7 @@ from .theme_cluster_factors import *
|
|
|
34
34
|
from .theme_feature_expansion import *
|
|
35
35
|
from .theme_feature_expansion_data import *
|
|
36
36
|
from .trading_data_utils import *
|
|
37
|
+
from .minute_data_reader import *
|
|
37
38
|
|
|
38
39
|
|
|
39
40
|
|
|
@@ -257,6 +258,7 @@ __all__ = [
|
|
|
257
258
|
"read_trade",
|
|
258
259
|
"read_market",
|
|
259
260
|
"read_market_pair",
|
|
261
|
+
"read_minute_data",
|
|
260
262
|
"get_features_factors_single",
|
|
261
263
|
"get_features_factors",
|
|
262
264
|
"get_features_names",
|
|
@@ -0,0 +1,191 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""factor-task — 因子计算任务 CLI 工具
|
|
3
|
+
|
|
4
|
+
通过 HTTP 与 factor_taskd 守护进程通信,管理因子计算任务。
|
|
5
|
+
|
|
6
|
+
用法:
|
|
7
|
+
factor-task submit <script.py> [--n-jobs N] [--start-date YYYYMMDD] [--end-date YYYYMMDD]
|
|
8
|
+
factor-task list
|
|
9
|
+
factor-task show <id>
|
|
10
|
+
factor-task cancel <id>
|
|
11
|
+
factor-task adjust <id> <n_jobs>
|
|
12
|
+
factor-task log <id>
|
|
13
|
+
"""
|
|
14
|
+
from __future__ import annotations
|
|
15
|
+
|
|
16
|
+
import argparse
|
|
17
|
+
import json
|
|
18
|
+
import os
|
|
19
|
+
import sys
|
|
20
|
+
import urllib.error
|
|
21
|
+
import urllib.request
|
|
22
|
+
|
|
23
|
+
DAEMON_URL = os.environ.get("FACTOR_TASK_URL", "http://127.0.0.1:9099")
|
|
24
|
+
TIMEOUT = 10
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
def _request(method: str, path: str, body: dict | None = None) -> dict:
|
|
28
|
+
url = f"{DAEMON_URL}{path}"
|
|
29
|
+
data = json.dumps(body).encode() if body else None
|
|
30
|
+
req = urllib.request.Request(url, data=data, method=method)
|
|
31
|
+
req.add_header("Content-Type", "application/json")
|
|
32
|
+
try:
|
|
33
|
+
with urllib.request.urlopen(req, timeout=TIMEOUT) as resp:
|
|
34
|
+
return json.loads(resp.read().decode())
|
|
35
|
+
except urllib.error.HTTPError as e:
|
|
36
|
+
err = e.read().decode()
|
|
37
|
+
print(f"❌ HTTP {e.code}: {err}", file=sys.stderr)
|
|
38
|
+
sys.exit(1)
|
|
39
|
+
except urllib.error.URLError as e:
|
|
40
|
+
print(f"❌ 连接失败 (确保 factor_taskd 正在运行): {e.reason}", file=sys.stderr)
|
|
41
|
+
sys.exit(1)
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
def cmd_submit(args):
|
|
45
|
+
body = {
|
|
46
|
+
"script_path": os.path.abspath(args.script),
|
|
47
|
+
"n_jobs": args.n_jobs or 50,
|
|
48
|
+
}
|
|
49
|
+
if args.start_date:
|
|
50
|
+
body["start_date"] = args.start_date
|
|
51
|
+
if args.end_date:
|
|
52
|
+
body["end_date"] = args.end_date
|
|
53
|
+
|
|
54
|
+
resp = _request("POST", "/api/tasks", body)
|
|
55
|
+
print(f"✅ 任务已提交")
|
|
56
|
+
print(f" 任务 ID: {resp['id']}")
|
|
57
|
+
print(f" 名称: {resp['name']}")
|
|
58
|
+
print(f" 状态: {resp['status']}")
|
|
59
|
+
print(f" 查看: factor-task show {resp['id']}")
|
|
60
|
+
|
|
61
|
+
|
|
62
|
+
def cmd_list(args):
|
|
63
|
+
tasks = _request("GET", "/api/tasks")
|
|
64
|
+
if not tasks:
|
|
65
|
+
print("📭 暂无任务")
|
|
66
|
+
return
|
|
67
|
+
print(f"{'ID':>4} {'名称':<20} {'状态':<12} {'n_jobs':<6} {'PID':<7} {'进度':<10}")
|
|
68
|
+
print("-" * 70)
|
|
69
|
+
for t in tasks:
|
|
70
|
+
progress = ""
|
|
71
|
+
if t.get("progress") and t["progress"].get("latest"):
|
|
72
|
+
latest = t["progress"]["latest"]
|
|
73
|
+
if "collected" in latest and "total_tasks" in latest:
|
|
74
|
+
pct = (
|
|
75
|
+
latest["collected"] / latest["total_tasks"] * 100
|
|
76
|
+
if latest["total_tasks"]
|
|
77
|
+
else 0
|
|
78
|
+
)
|
|
79
|
+
progress = f"{latest['collected']}/{latest['total_tasks']}({pct:.0f}%)"
|
|
80
|
+
pid = t.get("pid") or ""
|
|
81
|
+
n_jobs = t.get("n_jobs") or ""
|
|
82
|
+
status = t.get("status", "unknown")
|
|
83
|
+
print(
|
|
84
|
+
f"{t['id']:>4} {t.get('name',''):<20} {status:<12} {str(n_jobs):<6} {str(pid):<7} {progress:<10}"
|
|
85
|
+
)
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
def cmd_show(args):
|
|
89
|
+
task = _request("GET", f"/api/tasks/{args.id}")
|
|
90
|
+
print(f"任务 ID: {task['id']}")
|
|
91
|
+
print(f"名称: {task.get('name', '-')}")
|
|
92
|
+
print(f"脚本路径: {task.get('script_path', '-')}")
|
|
93
|
+
print(f"状态: {task.get('status', '-')}")
|
|
94
|
+
print(f"PID: {task.get('pid', '-')}")
|
|
95
|
+
print(f"n_jobs: {task.get('n_jobs', '-')}")
|
|
96
|
+
print(f"起止日期: {task.get('start_date', '-')} ~ {task.get('end_date', '-')}")
|
|
97
|
+
print(f"创建时间: {task.get('created_at', '-')}")
|
|
98
|
+
print(f"开始时间: {task.get('started_at', '-')}")
|
|
99
|
+
print(f"完成时间: {task.get('finished_at', '-')}")
|
|
100
|
+
print(f"日志路径: {task.get('log_path', '-')}")
|
|
101
|
+
print(f"运行中: {task.get('active', False)}")
|
|
102
|
+
if task.get("error"):
|
|
103
|
+
print(f"错误: {task['error']}")
|
|
104
|
+
|
|
105
|
+
progress = task.get("progress")
|
|
106
|
+
if progress and progress.get("records"):
|
|
107
|
+
records = progress["records"]
|
|
108
|
+
latest = progress.get("latest", {})
|
|
109
|
+
if "collected" in latest and "total_tasks" in latest:
|
|
110
|
+
pct = (
|
|
111
|
+
latest["collected"] / latest["total_tasks"] * 100
|
|
112
|
+
if latest["total_tasks"]
|
|
113
|
+
else 0
|
|
114
|
+
)
|
|
115
|
+
print(
|
|
116
|
+
f"进度: {latest['collected']}/{latest['total_tasks']} ({pct:.1f}%)"
|
|
117
|
+
)
|
|
118
|
+
if len(records) > 1:
|
|
119
|
+
last = records[-1]
|
|
120
|
+
print(
|
|
121
|
+
f"最后备份: {last.get('batch', '-')}/{last.get('total_batches', '-')}"
|
|
122
|
+
)
|
|
123
|
+
|
|
124
|
+
|
|
125
|
+
def cmd_cancel(args):
|
|
126
|
+
resp = _request("POST", f"/api/tasks/{args.id}/cancel")
|
|
127
|
+
print(f"✅ 任务 {args.id} 已取消")
|
|
128
|
+
|
|
129
|
+
|
|
130
|
+
def cmd_adjust(args):
|
|
131
|
+
body = {"n_jobs": args.n_jobs}
|
|
132
|
+
resp = _request("POST", f"/api/tasks/{args.id}/adjust-njobs", body)
|
|
133
|
+
print(f"✅ 任务 {args.id} n_jobs 已调整为 {args.n_jobs}")
|
|
134
|
+
|
|
135
|
+
|
|
136
|
+
def cmd_log(args):
|
|
137
|
+
resp = _request("GET", f"/api/tasks/{args.id}/log")
|
|
138
|
+
log = resp.get("log", "")
|
|
139
|
+
if log:
|
|
140
|
+
print(log)
|
|
141
|
+
else:
|
|
142
|
+
print("📭 日志为空")
|
|
143
|
+
|
|
144
|
+
|
|
145
|
+
def main():
|
|
146
|
+
parser = argparse.ArgumentParser(description="因子计算任务 CLI 工具")
|
|
147
|
+
parser.add_argument(
|
|
148
|
+
"--url", default=DAEMON_URL, help=f"daemon 地址 (默认: {DAEMON_URL})"
|
|
149
|
+
)
|
|
150
|
+
sub = parser.add_subparsers(dest="command")
|
|
151
|
+
|
|
152
|
+
p_submit = sub.add_parser("submit", help="提交新任务")
|
|
153
|
+
p_submit.add_argument("script", help="Python 脚本路径")
|
|
154
|
+
p_submit.add_argument("--n-jobs", type=int, default=None, help="并行数")
|
|
155
|
+
p_submit.add_argument("--start-date", type=int, help="起始日期 (YYYYMMDD)")
|
|
156
|
+
p_submit.add_argument("--end-date", type=int, help="结束日期 (YYYYMMDD)")
|
|
157
|
+
p_submit.set_defaults(func=cmd_submit)
|
|
158
|
+
|
|
159
|
+
p_list = sub.add_parser("list", help="列出所有任务")
|
|
160
|
+
p_list.set_defaults(func=cmd_list)
|
|
161
|
+
|
|
162
|
+
p_show = sub.add_parser("show", help="查看任务详情")
|
|
163
|
+
p_show.add_argument("id", type=int, help="任务 ID")
|
|
164
|
+
p_show.set_defaults(func=cmd_show)
|
|
165
|
+
|
|
166
|
+
p_cancel = sub.add_parser("cancel", help="取消任务")
|
|
167
|
+
p_cancel.add_argument("id", type=int, help="任务 ID")
|
|
168
|
+
p_cancel.set_defaults(func=cmd_cancel)
|
|
169
|
+
|
|
170
|
+
p_adjust = sub.add_parser("adjust", help="调节并行数")
|
|
171
|
+
p_adjust.add_argument("id", type=int, help="任务 ID")
|
|
172
|
+
p_adjust.add_argument("n_jobs", type=int, help="新的并行数")
|
|
173
|
+
p_adjust.set_defaults(func=cmd_adjust)
|
|
174
|
+
|
|
175
|
+
p_log = sub.add_parser("log", help="查看任务日志")
|
|
176
|
+
p_log.add_argument("id", type=int, help="任务 ID")
|
|
177
|
+
p_log.set_defaults(func=cmd_log)
|
|
178
|
+
|
|
179
|
+
args = parser.parse_args()
|
|
180
|
+
if not args.command:
|
|
181
|
+
parser.print_help()
|
|
182
|
+
sys.exit(1)
|
|
183
|
+
|
|
184
|
+
import factor_task # noqa: F811
|
|
185
|
+
factor_task.DAEMON_URL = args.url
|
|
186
|
+
|
|
187
|
+
args.func(args)
|
|
188
|
+
|
|
189
|
+
|
|
190
|
+
if __name__ == "__main__":
|
|
191
|
+
main()
|