quantnodes 3.0.0__py3-none-any.whl
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.
- QuantNodes/__init__.py +15 -0
- QuantNodes/__main__.py +14 -0
- QuantNodes/agent/__init__.py +158 -0
- QuantNodes/agent/agents/__init__.py +13 -0
- QuantNodes/agent/agents/definition.py +180 -0
- QuantNodes/agent/agents/manager.py +73 -0
- QuantNodes/agent/config/__init__.py +34 -0
- QuantNodes/agent/config/executor.py +958 -0
- QuantNodes/agent/config/loader.py +427 -0
- QuantNodes/agent/config/templates/bollinger_bands.yaml +84 -0
- QuantNodes/agent/config/templates/dual_ma.yaml +72 -0
- QuantNodes/agent/config/templates/empty.yaml +56 -0
- QuantNodes/agent/config/templates/mean_reversion.yaml +47 -0
- QuantNodes/agent/config/templates/mean_reversion_zscore.yaml +90 -0
- QuantNodes/agent/config/templates/momentum.yaml +81 -0
- QuantNodes/agent/config/templates/momentum_breakout.yaml +84 -0
- QuantNodes/agent/config/templates/rsi_strategy.yaml +72 -0
- QuantNodes/agent/config/templates/volume_price.yaml +86 -0
- QuantNodes/agent/config/types.py +156 -0
- QuantNodes/agent/config_mapper.py +293 -0
- QuantNodes/agent/core/__init__.py +19 -0
- QuantNodes/agent/core/dream.py +47 -0
- QuantNodes/agent/core/quant_dream.py +274 -0
- QuantNodes/agent/cron_jobs.py +314 -0
- QuantNodes/agent/nanobot_bridge.py +242 -0
- QuantNodes/agent/permission/__init__.py +30 -0
- QuantNodes/agent/permission/defaults.py +36 -0
- QuantNodes/agent/permission/evaluate.py +41 -0
- QuantNodes/agent/permission/models.py +59 -0
- QuantNodes/agent/permission/service.py +133 -0
- QuantNodes/agent/providers/__init__.py +11 -0
- QuantNodes/agent/providers/base.py +102 -0
- QuantNodes/agent/providers/quantnodes.py +610 -0
- QuantNodes/agent/providers/rate_limiter.py +326 -0
- QuantNodes/agent/providers/registry.py +163 -0
- QuantNodes/agent/skills/__init__.py +20 -0
- QuantNodes/agent/skills/base.py +118 -0
- QuantNodes/agent/skills/bridge.py +73 -0
- QuantNodes/agent/skills/factor/__init__.py +14 -0
- QuantNodes/agent/skills/factor/correlation.py +99 -0
- QuantNodes/agent/skills/factor/group_backtest.py +114 -0
- QuantNodes/agent/skills/factor/ic_analysis.py +106 -0
- QuantNodes/agent/skills/loader.py +107 -0
- QuantNodes/agent/skills/registry.py +105 -0
- QuantNodes/agent/skills/strategy/__init__.py +16 -0
- QuantNodes/agent/skills/strategy/bollinger.py +86 -0
- QuantNodes/agent/skills/strategy/dual_ma.py +82 -0
- QuantNodes/agent/skills/strategy/momentum.py +74 -0
- QuantNodes/agent/skills/strategy/rsi_reversal.py +99 -0
- QuantNodes/agent/skills_quant/__init__.py +14 -0
- QuantNodes/agent/skills_quant/backtest-analyze/SKILL.md +42 -0
- QuantNodes/agent/skills_quant/config-driven/SKILL.md +72 -0
- QuantNodes/agent/skills_quant/factor-research/SKILL.md +40 -0
- QuantNodes/agent/skills_quant/quant-dream/SKILL.md +55 -0
- QuantNodes/agent/skills_quant/risk-management/SKILL.md +45 -0
- QuantNodes/agent/skills_quant/strategy-design/SKILL.md +43 -0
- QuantNodes/agent/templates/__init__.py +4 -0
- QuantNodes/agent/tools/__init__.py +173 -0
- QuantNodes/agent/tools/_workspace.py +51 -0
- QuantNodes/agent/tools/alpha_backtest.py +328 -0
- QuantNodes/agent/tools/alpha_evaluate.py +493 -0
- QuantNodes/agent/tools/backtest.py +226 -0
- QuantNodes/agent/tools/base.py +133 -0
- QuantNodes/agent/tools/code_search.py +207 -0
- QuantNodes/agent/tools/config_backtest.py +401 -0
- QuantNodes/agent/tools/context.py +97 -0
- QuantNodes/agent/tools/dream_skill.py +77 -0
- QuantNodes/agent/tools/echo.py +38 -0
- QuantNodes/agent/tools/factor.py +231 -0
- QuantNodes/agent/tools/file_ops.py +201 -0
- QuantNodes/agent/tools/git_ops.py +190 -0
- QuantNodes/agent/tools/operator_lookup.py +218 -0
- QuantNodes/agent/tools/output_truncation.py +77 -0
- QuantNodes/agent/tools/path_check.py +43 -0
- QuantNodes/agent/tools/pipeline.py +62 -0
- QuantNodes/agent/tools/registry.py +150 -0
- QuantNodes/agent/tools/sandbox.py +62 -0
- QuantNodes/agent/tools/shell_safety.py +63 -0
- QuantNodes/agent/tools/strategy.py +106 -0
- QuantNodes/agent/tools/task.py +171 -0
- QuantNodes/agent/tools/web_fetch.py +142 -0
- QuantNodes/agent/tools/web_search.py +114 -0
- QuantNodes/agent/tools/wiki.py +370 -0
- QuantNodes/agent/utils/__init__.py +11 -0
- QuantNodes/agent/utils/helpers.py +43 -0
- QuantNodes/agent/utils/prompt_templates.py +30 -0
- QuantNodes/agent/workflows/__init__.py +20 -0
- QuantNodes/agent/workflows/implementations/__init__.py +8 -0
- QuantNodes/agent/workflows/implementations/alpha_gpt.py +508 -0
- QuantNodes/agent/workflows/implementations/mcts.py +442 -0
- QuantNodes/agent/workflows/parsers.py +44 -0
- QuantNodes/agent/workflows/registry.py +119 -0
- QuantNodes/agent/workflows/step_agent.py +219 -0
- QuantNodes/agent/workflows/tool.py +198 -0
- QuantNodes/ai/__init__.py +93 -0
- QuantNodes/ai/llm/__init__.py +75 -0
- QuantNodes/ai/llm/base.py +233 -0
- QuantNodes/ai/llm/decorators.py +281 -0
- QuantNodes/ai/llm/gateway.py +571 -0
- QuantNodes/ai/llm/null.py +76 -0
- QuantNodes/ai/llm/openai.py +435 -0
- QuantNodes/ai/optimizer.py +405 -0
- QuantNodes/ai/prompts/__init__.py +229 -0
- QuantNodes/ai/sandbox.py +371 -0
- QuantNodes/ai/sandbox_pandas_bridge.py +150 -0
- QuantNodes/ai/strategy_gen.py +396 -0
- QuantNodes/backtest/__init__.py +64 -0
- QuantNodes/backtest/backtest_node.py +188 -0
- QuantNodes/backtest/broker_node.py +378 -0
- QuantNodes/backtest/config_runner.py +397 -0
- QuantNodes/backtest/config_strategy.py +64 -0
- QuantNodes/backtest/risk_node.py +360 -0
- QuantNodes/backtest/strategy_node.py +268 -0
- QuantNodes/cache_node/__init__.py +19 -0
- QuantNodes/cache_node/base.py +244 -0
- QuantNodes/cache_node/cache_store.py +99 -0
- QuantNodes/cache_node/metadata.py +100 -0
- QuantNodes/cli/__init__.py +109 -0
- QuantNodes/cli/_helpers.py +511 -0
- QuantNodes/cli/command.py +110 -0
- QuantNodes/cli/commands/__init__.py +69 -0
- QuantNodes/cli/commands/agent.py +158 -0
- QuantNodes/cli/commands/alpha.py +951 -0
- QuantNodes/cli/commands/chat.py +38 -0
- QuantNodes/cli/commands/evolve.py +120 -0
- QuantNodes/cli/commands/factor.py +569 -0
- QuantNodes/cli/commands/init.py +190 -0
- QuantNodes/cli/commands/run.py +259 -0
- QuantNodes/cli/commands/serve.py +398 -0
- QuantNodes/cli/commands/version.py +120 -0
- QuantNodes/cli/enhanced.py +146 -0
- QuantNodes/conf_node/__init__.py +37 -0
- QuantNodes/conf_node/base.py +120 -0
- QuantNodes/conf_node/env_config.py +132 -0
- QuantNodes/conf_node/ini_config.py +70 -0
- QuantNodes/conf_node/json_config.py +69 -0
- QuantNodes/conf_node/yaml_config.py +78 -0
- QuantNodes/constants.py +17 -0
- QuantNodes/core/__init__.py +196 -0
- QuantNodes/core/_lookback_helpers.py +49 -0
- QuantNodes/core/ast_parser.py +198 -0
- QuantNodes/core/base.py +61 -0
- QuantNodes/core/cache_manager.py +344 -0
- QuantNodes/core/cache_utils.py +150 -0
- QuantNodes/core/cond_builder.py +53 -0
- QuantNodes/core/config.py +170 -0
- QuantNodes/core/constants.py +48 -0
- QuantNodes/core/control.py +412 -0
- QuantNodes/core/data_preprocessing.py +453 -0
- QuantNodes/core/data_source.py +46 -0
- QuantNodes/core/events.py +178 -0
- QuantNodes/core/evolution/__init__.py +22 -0
- QuantNodes/core/evolution/loop.py +583 -0
- QuantNodes/core/evolution/operators.py +289 -0
- QuantNodes/core/evolution/settings.py +44 -0
- QuantNodes/core/expression.py +841 -0
- QuantNodes/core/feedback/__init__.py +38 -0
- QuantNodes/core/feedback/channels.py +182 -0
- QuantNodes/core/feedback/collector.py +91 -0
- QuantNodes/core/feedback/dataclass.py +239 -0
- QuantNodes/core/feedback/llm_judge.py +138 -0
- QuantNodes/core/knowledge/__init__.py +69 -0
- QuantNodes/core/knowledge/knowledge_base.py +217 -0
- QuantNodes/core/knowledge/lineage_compress.py +196 -0
- QuantNodes/core/knowledge/lineage_expand.py +123 -0
- QuantNodes/core/knowledge/metrics/__init__.py +43 -0
- QuantNodes/core/knowledge/metrics/evaluator.py +176 -0
- QuantNodes/core/knowledge/metrics/metrics.py +220 -0
- QuantNodes/core/knowledge/rag_prompt.py +196 -0
- QuantNodes/core/knowledge/retriever.py +209 -0
- QuantNodes/core/lambda_node.py +81 -0
- QuantNodes/core/monitoring/__init__.py +22 -0
- QuantNodes/core/monitoring/collector.py +292 -0
- QuantNodes/core/monitoring/dashboard.py +365 -0
- QuantNodes/core/node.py +375 -0
- QuantNodes/core/pandas_utils.py +504 -0
- QuantNodes/core/parallel/__init__.py +15 -0
- QuantNodes/core/parallel/worker.py +140 -0
- QuantNodes/core/parallel/worker_process.py +265 -0
- QuantNodes/core/path_utils.py +73 -0
- QuantNodes/core/pipeline.py +328 -0
- QuantNodes/core/plugin.py +135 -0
- QuantNodes/core/quality_gate/__init__.py +32 -0
- QuantNodes/core/quality_gate/complexity.py +94 -0
- QuantNodes/core/quality_gate/consistency.py +26 -0
- QuantNodes/core/quality_gate/node.py +97 -0
- QuantNodes/core/quality_gate/redundancy.py +51 -0
- QuantNodes/core/quality_gate/settings.py +43 -0
- QuantNodes/core/quality_gate/zoo.py +98 -0
- QuantNodes/core/serializable.py +116 -0
- QuantNodes/core/serialization.py +673 -0
- QuantNodes/core/tools.py +333 -0
- QuantNodes/core/trajectory/__init__.py +25 -0
- QuantNodes/core/trajectory/entry.py +116 -0
- QuantNodes/core/trajectory/lineage.py +67 -0
- QuantNodes/core/trajectory/pool.py +211 -0
- QuantNodes/core/trajectory/selector.py +140 -0
- QuantNodes/core/visualization/__init__.py +33 -0
- QuantNodes/core/visualization/builder.py +233 -0
- QuantNodes/core/visualization/gate_breakdown.py +140 -0
- QuantNodes/core/visualization/lineage_dag.py +203 -0
- QuantNodes/core/visualization/metric_distribution.py +125 -0
- QuantNodes/core/visualization/report.py +68 -0
- QuantNodes/database_node/__init__.py +69 -0
- QuantNodes/database_node/base.py +135 -0
- QuantNodes/database_node/clickhouse_node.py +272 -0
- QuantNodes/database_node/csv_node.py +83 -0
- QuantNodes/database_node/duckdb_node.py +86 -0
- QuantNodes/database_node/factory.py +83 -0
- QuantNodes/database_node/mysql_node.py +100 -0
- QuantNodes/database_node/parquet_node.py +75 -0
- QuantNodes/database_node/sqlite_node.py +67 -0
- QuantNodes/factor_node/__init__.py +50 -0
- QuantNodes/factor_node/factor.py +563 -0
- QuantNodes/factor_node/factor_db.py +421 -0
- QuantNodes/factor_node/factor_functions/__init__.py +252 -0
- QuantNodes/factor_node/factor_functions/_helpers.py +358 -0
- QuantNodes/factor_node/factor_functions/_helpers_debug.py +317 -0
- QuantNodes/factor_node/factor_functions/composite_ops.py +136 -0
- QuantNodes/factor_node/factor_functions/math_ops.py +433 -0
- QuantNodes/factor_node/factor_functions/section_ops.py +290 -0
- QuantNodes/factor_node/factor_functions/talib_ops.py +1293 -0
- QuantNodes/factor_node/factor_functions/time_ops.py +535 -0
- QuantNodes/factor_node/factor_operation.py +1115 -0
- QuantNodes/factor_node/factor_table.py +1073 -0
- QuantNodes/factor_node/quant_nodes_object.py +60 -0
- QuantNodes/mcp_server/__init__.py +27 -0
- QuantNodes/mcp_server/__main__.py +4 -0
- QuantNodes/mcp_server/server.py +272 -0
- QuantNodes/methods/__init__.py +28 -0
- QuantNodes/methods/pipeline.py +100 -0
- QuantNodes/methods/sandbox.py +102 -0
- QuantNodes/monitor/__init__.py +27 -0
- QuantNodes/monitor/agent_tools/__init__.py +5 -0
- QuantNodes/monitor/agent_tools/monitor_tool.py +98 -0
- QuantNodes/monitor/agent_tools/schedule_tool.py +98 -0
- QuantNodes/monitor/agent_tools/version_tool.py +133 -0
- QuantNodes/monitor/monitor/__init__.py +6 -0
- QuantNodes/monitor/monitor/alerter.py +60 -0
- QuantNodes/monitor/monitor/collector.py +164 -0
- QuantNodes/monitor/monitor/dashboard.py +115 -0
- QuantNodes/monitor/monitor/drift.py +190 -0
- QuantNodes/monitor/scheduler/__init__.py +4 -0
- QuantNodes/monitor/scheduler/runner.py +133 -0
- QuantNodes/monitor/scheduler/scheduler.py +184 -0
- QuantNodes/monitor/storage/__init__.py +16 -0
- QuantNodes/monitor/storage/models.py +70 -0
- QuantNodes/monitor/storage/repository.py +407 -0
- QuantNodes/monitor/version/__init__.py +4 -0
- QuantNodes/monitor/version/diff.py +81 -0
- QuantNodes/monitor/version/version_manager.py +182 -0
- QuantNodes/operator_node/__init__.py +28 -0
- QuantNodes/operator_node/base.py +97 -0
- QuantNodes/operator_node/query_node.py +129 -0
- QuantNodes/operator_node/sql_builder.py +125 -0
- QuantNodes/operator_node/sql_utils.py +172 -0
- QuantNodes/operator_node/transform.py +130 -0
- QuantNodes/operators/__init__.py +90 -0
- QuantNodes/operators/_engine.py +108 -0
- QuantNodes/operators/composite.py +161 -0
- QuantNodes/operators/composite_dag.py +667 -0
- QuantNodes/operators/composite_dag_ops.py +343 -0
- QuantNodes/operators/composite_dag_pandas_ops.py +382 -0
- QuantNodes/operators/custom.py +408 -0
- QuantNodes/operators/facade.py +164 -0
- QuantNodes/operators/math.py +163 -0
- QuantNodes/operators/proxy.py +29 -0
- QuantNodes/operators/registry.py +144 -0
- QuantNodes/operators/section.py +99 -0
- QuantNodes/operators/talib.py +757 -0
- QuantNodes/operators/templates.py +95 -0
- QuantNodes/operators/time_series.py +136 -0
- QuantNodes/prompts/__init__.py +20 -0
- QuantNodes/prompts/backtest/__init__.py +12 -0
- QuantNodes/prompts/backtest/factor_based.py +86 -0
- QuantNodes/prompts/backtest/standard.py +73 -0
- QuantNodes/prompts/factor/__init__.py +14 -0
- QuantNodes/prompts/factor/correlation.py +77 -0
- QuantNodes/prompts/factor/group_backtest.py +86 -0
- QuantNodes/prompts/factor/ic_analysis.py +91 -0
- QuantNodes/prompts/strategy/__init__.py +18 -0
- QuantNodes/prompts/strategy/market_neutral.py +96 -0
- QuantNodes/prompts/strategy/mean_reversion.py +107 -0
- QuantNodes/prompts/strategy/momentum.py +160 -0
- QuantNodes/prompts/strategy/pairs_trading.py +107 -0
- QuantNodes/prompts/strategy/trend_following.py +96 -0
- QuantNodes/research/README.md +106 -0
- QuantNodes/research/__init__.py +154 -0
- QuantNodes/research/_legacy_3c/__init__.py +61 -0
- QuantNodes/research/_legacy_3c/auto_researcher.py +289 -0
- QuantNodes/research/_legacy_3c/factor_evaluator.py +560 -0
- QuantNodes/research/_legacy_3c/factor_miner.py +318 -0
- QuantNodes/research/_legacy_3c/mcts_search.py +324 -0
- QuantNodes/research/factor_test/__init__.py +25 -0
- QuantNodes/research/factor_test/config.py +184 -0
- QuantNodes/research/factor_test/config_builder.py +276 -0
- QuantNodes/research/factor_test/e2e/data_prep.py +163 -0
- QuantNodes/research/factor_test/e2e/run_evolution_e2e.py +309 -0
- QuantNodes/research/factor_test/evolution_adapter.py +231 -0
- QuantNodes/research/factor_test/feedback_wrapper.py +102 -0
- QuantNodes/research/factor_test/ifind_db/__init__.py +7 -0
- QuantNodes/research/factor_test/ifind_db/fetcher.py +224 -0
- QuantNodes/research/factor_test/ifind_db/ifind_database.py +689 -0
- QuantNodes/research/factor_test/nodes/__init__.py +1 -0
- QuantNodes/research/factor_test/nodes/_base.py +91 -0
- QuantNodes/research/factor_test/nodes/adjust_date_node.py +48 -0
- QuantNodes/research/factor_test/nodes/configs.py +240 -0
- QuantNodes/research/factor_test/nodes/factor_neutralize_node.py +87 -0
- QuantNodes/research/factor_test/nodes/factor_preprocess_node.py +222 -0
- QuantNodes/research/factor_test/nodes/factor_score_node.py +141 -0
- QuantNodes/research/factor_test/nodes/factor_test_report_node.py +153 -0
- QuantNodes/research/factor_test/nodes/group_analyzer_node.py +317 -0
- QuantNodes/research/factor_test/nodes/ic_analyzer_node.py +112 -0
- QuantNodes/research/factor_test/nodes/load_data_node.py +100 -0
- QuantNodes/research/factor_test/nodes/long_short_node.py +93 -0
- QuantNodes/research/factor_test/nodes/neutralizers.py +222 -0
- QuantNodes/research/factor_test/nodes/preprocess_strategies.py +277 -0
- QuantNodes/research/factor_test/nodes/risk_correlation_node.py +112 -0
- QuantNodes/research/factor_test/nodes/sample_pool_filter_node.py +110 -0
- QuantNodes/research/factor_test/nodes/tradability_filter_node.py +92 -0
- QuantNodes/research/factor_test/pipeline_runner.py +305 -0
- QuantNodes/research/factor_test/pipeline_spec.py +216 -0
- QuantNodes/research/factor_test/utils/__init__.py +26 -0
- QuantNodes/research/factor_test/utils/constants.py +86 -0
- QuantNodes/research/factor_test/utils/data_loader.py +141 -0
- QuantNodes/research/factor_test/utils/date_utils.py +232 -0
- QuantNodes/research/factor_test/utils/file_loaders.py +150 -0
- QuantNodes/research/factor_test/utils/labels.py +37 -0
- QuantNodes/research/factor_test/utils/metrics_extractor.py +55 -0
- QuantNodes/research/factor_test/utils/performance_metrics.py +175 -0
- QuantNodes/research/factor_test/utils/safe_load.py +106 -0
- QuantNodes/research/quant_alpha/CHANGELOG.md +80 -0
- QuantNodes/research/quant_alpha/README.md +142 -0
- QuantNodes/research/quant_alpha/__init__.py +45 -0
- QuantNodes/research/quant_alpha/adapters/__init__.py +99 -0
- QuantNodes/research/quant_alpha/adapters/calculator.py +503 -0
- QuantNodes/research/quant_alpha/adapters/expression.py +387 -0
- QuantNodes/research/quant_alpha/alpha101_design/__init__.py +50 -0
- QuantNodes/research/quant_alpha/alpha101_design/few_shot_examples.py +243 -0
- QuantNodes/research/quant_alpha/alpha101_design/philosophy.py +474 -0
- QuantNodes/research/quant_alpha/alpha158_design/__init__.py +63 -0
- QuantNodes/research/quant_alpha/alpha158_design/few_shot_examples.py +219 -0
- QuantNodes/research/quant_alpha/alpha158_design/philosophy.py +240 -0
- QuantNodes/research/quant_alpha/evaluation/__init__.py +47 -0
- QuantNodes/research/quant_alpha/evaluation/baselines/__init__.py +8 -0
- QuantNodes/research/quant_alpha/evaluation/baselines/g1_handcrafted.py +135 -0
- QuantNodes/research/quant_alpha/evaluation/baselines/g2_llm_only.py +269 -0
- QuantNodes/research/quant_alpha/evaluation/baselines/g3_alpha_gpt.py +152 -0
- QuantNodes/research/quant_alpha/evaluation/clickhouse_data_loader.py +227 -0
- QuantNodes/research/quant_alpha/evaluation/contracts.py +376 -0
- QuantNodes/research/quant_alpha/evaluation/evaluators/__init__.py +6 -0
- QuantNodes/research/quant_alpha/evaluation/evaluators/polars_evaluator.py +545 -0
- QuantNodes/research/quant_alpha/evaluation/mock_data_loader.py +226 -0
- QuantNodes/research/quant_alpha/evaluation/runner.py +243 -0
- QuantNodes/research/quant_alpha/llm/__init__.py +38 -0
- QuantNodes/research/quant_alpha/llm/parser.py +681 -0
- QuantNodes/research/quant_alpha/logic_driven_pipeline.py +411 -0
- QuantNodes/research/quant_alpha/logic_mining/__init__.py +74 -0
- QuantNodes/research/quant_alpha/logic_mining/compiler.py +457 -0
- QuantNodes/research/quant_alpha/logic_mining/generator.py +366 -0
- QuantNodes/research/quant_alpha/logic_mining/models.py +252 -0
- QuantNodes/research/quant_alpha/logic_mining/parser.py +287 -0
- QuantNodes/research/quant_alpha/logic_mining/pipelines.py +297 -0
- QuantNodes/research/quant_alpha/logic_mining/sources.py +149 -0
- QuantNodes/research/quant_alpha/mcts/__init__.py +66 -0
- QuantNodes/research/quant_alpha/mcts/cache.py +262 -0
- QuantNodes/research/quant_alpha/mcts/extension_ops.py +320 -0
- QuantNodes/research/quant_alpha/mcts/feedback.py +825 -0
- QuantNodes/research/quant_alpha/mcts/op_prior.py +180 -0
- QuantNodes/research/quant_alpha/mcts/search.py +540 -0
- QuantNodes/research/quant_alpha/mcts/tree.py +201 -0
- QuantNodes/research/quant_alpha/operator_vocab/__init__.py +50 -0
- QuantNodes/research/quant_alpha/operator_vocab/config.py +54 -0
- QuantNodes/research/quant_alpha/operator_vocab/metadata.py +263 -0
- QuantNodes/research/quant_alpha/operator_vocab/vocabulary.py +481 -0
- QuantNodes/research/quant_alpha/pipeline.py +1027 -0
- QuantNodes/research/quant_alpha/types/__init__.py +27 -0
- QuantNodes/research/quant_alpha/types/constants.py +28 -0
- QuantNodes/research/quant_alpha/types/state.py +205 -0
- QuantNodes/research/quant_alpha/workflow/__init__.py +32 -0
- QuantNodes/research/quant_alpha/workflow/alpha_gpt.py +911 -0
- QuantNodes/research/quant_alpha/workflow/alpha_logics.py +416 -0
- QuantNodes/research/quant_alpha/workflow/state.py +27 -0
- QuantNodes/research/report_reproducer.py +485 -0
- QuantNodes/research/wiki.py +1155 -0
- QuantNodes/symbolic/__init__.py +51 -0
- QuantNodes/symbolic/compiler.py +113 -0
- QuantNodes/symbolic/dialect.py +260 -0
- QuantNodes/symbolic/executor.py +147 -0
- QuantNodes/symbolic/expression.py +234 -0
- QuantNodes/symbolic/functions.py +433 -0
- QuantNodes/symbolic/optimizer.py +165 -0
- QuantNodes/ui_node/__init__.py +30 -0
- QuantNodes/ui_node/base.py +222 -0
- quantnodes-3.0.0.dist-info/METADATA +463 -0
- quantnodes-3.0.0.dist-info/RECORD +399 -0
- quantnodes-3.0.0.dist-info/WHEEL +5 -0
- quantnodes-3.0.0.dist-info/entry_points.txt +24 -0
- quantnodes-3.0.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,234 @@
|
|
|
1
|
+
# coding=utf-8
|
|
2
|
+
"""
|
|
3
|
+
符号计算引擎 - SQL 表达式节点
|
|
4
|
+
|
|
5
|
+
定义用于 SQL 编译的表达式 AST 节点。
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from __future__ import annotations
|
|
9
|
+
|
|
10
|
+
from abc import ABC, abstractmethod
|
|
11
|
+
from typing import Any, List, Optional, Tuple
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
class SQLExpression(ABC):
|
|
15
|
+
"""SQL 表达式基类"""
|
|
16
|
+
|
|
17
|
+
@abstractmethod
|
|
18
|
+
def to_sql(self, dialect: "SQLDialect") -> str: # noqa: F821
|
|
19
|
+
"""编译为 SQL 字符串"""
|
|
20
|
+
pass
|
|
21
|
+
|
|
22
|
+
def __add__(self, other: Any) -> "SQLBinaryOp":
|
|
23
|
+
return SQLBinaryOp(self, "+", wrap_sql_expr(other))
|
|
24
|
+
|
|
25
|
+
def __radd__(self, other: Any) -> "SQLBinaryOp":
|
|
26
|
+
return SQLBinaryOp(wrap_sql_expr(other), "+", self)
|
|
27
|
+
|
|
28
|
+
def __sub__(self, other: Any) -> "SQLBinaryOp":
|
|
29
|
+
return SQLBinaryOp(self, "-", wrap_sql_expr(other))
|
|
30
|
+
|
|
31
|
+
def __rsub__(self, other: Any) -> "SQLBinaryOp":
|
|
32
|
+
return SQLBinaryOp(wrap_sql_expr(other), "-", self)
|
|
33
|
+
|
|
34
|
+
def __mul__(self, other: Any) -> "SQLBinaryOp":
|
|
35
|
+
return SQLBinaryOp(self, "*", wrap_sql_expr(other))
|
|
36
|
+
|
|
37
|
+
def __rmul__(self, other: Any) -> "SQLBinaryOp":
|
|
38
|
+
return SQLBinaryOp(wrap_sql_expr(other), "*", self)
|
|
39
|
+
|
|
40
|
+
def __truediv__(self, other: Any) -> "SQLBinaryOp":
|
|
41
|
+
return SQLBinaryOp(self, "/", wrap_sql_expr(other))
|
|
42
|
+
|
|
43
|
+
def __rtruediv__(self, other: Any) -> "SQLBinaryOp":
|
|
44
|
+
return SQLBinaryOp(wrap_sql_expr(other), "/", self)
|
|
45
|
+
|
|
46
|
+
def __neg__(self) -> "SQLUnaryOp":
|
|
47
|
+
return SQLUnaryOp("-", self)
|
|
48
|
+
|
|
49
|
+
def __gt__(self, other: Any) -> "SQLComparison":
|
|
50
|
+
return SQLComparison(self, ">", wrap_sql_expr(other))
|
|
51
|
+
|
|
52
|
+
def __ge__(self, other: Any) -> "SQLComparison":
|
|
53
|
+
return SQLComparison(self, ">=", wrap_sql_expr(other))
|
|
54
|
+
|
|
55
|
+
def __lt__(self, other: Any) -> "SQLComparison":
|
|
56
|
+
return SQLComparison(self, "<", wrap_sql_expr(other))
|
|
57
|
+
|
|
58
|
+
def __le__(self, other: Any) -> "SQLComparison":
|
|
59
|
+
return SQLComparison(self, "<=", wrap_sql_expr(other))
|
|
60
|
+
|
|
61
|
+
def __eq__(self, other: Any) -> "SQLComparison":
|
|
62
|
+
return SQLComparison(self, "==", wrap_sql_expr(other))
|
|
63
|
+
|
|
64
|
+
def __ne__(self, other: Any) -> "SQLComparison":
|
|
65
|
+
return SQLComparison(self, "!=", wrap_sql_expr(other))
|
|
66
|
+
|
|
67
|
+
def __and__(self, other: Any) -> "SQLLogicalOp":
|
|
68
|
+
return SQLLogicalOp("AND", self, wrap_sql_expr(other))
|
|
69
|
+
|
|
70
|
+
def __or__(self, other: Any) -> "SQLLogicalOp":
|
|
71
|
+
return SQLLogicalOp("OR", self, wrap_sql_expr(other))
|
|
72
|
+
|
|
73
|
+
def __invert__(self) -> "SQLLogicalOp":
|
|
74
|
+
return SQLLogicalOp("NOT", self)
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
class ColumnRef(SQLExpression):
|
|
78
|
+
"""列引用表达式"""
|
|
79
|
+
|
|
80
|
+
def __init__(self, name: str, table: Optional[str] = None):
|
|
81
|
+
self.name = name
|
|
82
|
+
self.table = table
|
|
83
|
+
|
|
84
|
+
def to_sql(self, dialect) -> str:
|
|
85
|
+
if self.table:
|
|
86
|
+
return f"{dialect.quote_identifier(self.table)}.{dialect.quote_identifier(self.name)}"
|
|
87
|
+
return dialect.quote_identifier(self.name)
|
|
88
|
+
|
|
89
|
+
def __repr__(self) -> str:
|
|
90
|
+
if self.table:
|
|
91
|
+
return f"{self.table}.{self.name}"
|
|
92
|
+
return self.name
|
|
93
|
+
|
|
94
|
+
|
|
95
|
+
class LiteralValue(SQLExpression):
|
|
96
|
+
"""字面量值表达式"""
|
|
97
|
+
|
|
98
|
+
def __init__(self, value: Any):
|
|
99
|
+
self.value = value
|
|
100
|
+
|
|
101
|
+
def to_sql(self, dialect) -> str:
|
|
102
|
+
return dialect.quote_literal(self.value)
|
|
103
|
+
|
|
104
|
+
def __repr__(self) -> str:
|
|
105
|
+
return repr(self.value)
|
|
106
|
+
|
|
107
|
+
|
|
108
|
+
class SQLBinaryOp(SQLExpression):
|
|
109
|
+
"""二元运算表达式"""
|
|
110
|
+
|
|
111
|
+
def __init__(self, left: SQLExpression, op: str, right: SQLExpression):
|
|
112
|
+
self.left = left
|
|
113
|
+
self.op = op
|
|
114
|
+
self.right = right
|
|
115
|
+
|
|
116
|
+
def to_sql(self, dialect) -> str:
|
|
117
|
+
left_sql = self.left.to_sql(dialect)
|
|
118
|
+
right_sql = self.right.to_sql(dialect)
|
|
119
|
+
return f"({left_sql} {self.op} {right_sql})"
|
|
120
|
+
|
|
121
|
+
def __repr__(self) -> str:
|
|
122
|
+
return f"({self.left} {self.op} {self.right})"
|
|
123
|
+
|
|
124
|
+
|
|
125
|
+
class SQLUnaryOp(SQLExpression):
|
|
126
|
+
"""一元运算表达式"""
|
|
127
|
+
|
|
128
|
+
def __init__(self, op: str, operand: SQLExpression):
|
|
129
|
+
self.op = op
|
|
130
|
+
self.operand = operand
|
|
131
|
+
|
|
132
|
+
def to_sql(self, dialect) -> str:
|
|
133
|
+
operand_sql = self.operand.to_sql(dialect)
|
|
134
|
+
return f"({self.op} {operand_sql})"
|
|
135
|
+
|
|
136
|
+
def __repr__(self) -> str:
|
|
137
|
+
return f"({self.op} {self.operand})"
|
|
138
|
+
|
|
139
|
+
|
|
140
|
+
class SQLComparison(SQLExpression):
|
|
141
|
+
"""比较运算表达式"""
|
|
142
|
+
|
|
143
|
+
def __init__(self, left: SQLExpression, op: str, right: SQLExpression):
|
|
144
|
+
self.left = left
|
|
145
|
+
self.op = op
|
|
146
|
+
self.right = right
|
|
147
|
+
|
|
148
|
+
def to_sql(self, dialect) -> str:
|
|
149
|
+
left_sql = self.left.to_sql(dialect)
|
|
150
|
+
right_sql = self.right.to_sql(dialect)
|
|
151
|
+
return f"({left_sql} {self.op} {right_sql})"
|
|
152
|
+
|
|
153
|
+
def __repr__(self) -> str:
|
|
154
|
+
return f"({self.left} {self.op} {self.right})"
|
|
155
|
+
|
|
156
|
+
|
|
157
|
+
class SQLLogicalOp(SQLExpression):
|
|
158
|
+
"""逻辑运算表达式"""
|
|
159
|
+
|
|
160
|
+
def __init__(self, op: str, *operands: SQLExpression):
|
|
161
|
+
self.op = op
|
|
162
|
+
self.operands = operands
|
|
163
|
+
|
|
164
|
+
def to_sql(self, dialect) -> str:
|
|
165
|
+
if self.op == "NOT":
|
|
166
|
+
operand_sql = self.operands[0].to_sql(dialect)
|
|
167
|
+
return f"(NOT {operand_sql})"
|
|
168
|
+
parts = [op.to_sql(dialect) for op in self.operands]
|
|
169
|
+
return "(" + self.op + " " + " ".join(parts) + ")"
|
|
170
|
+
|
|
171
|
+
def __repr__(self) -> str:
|
|
172
|
+
if self.op == "NOT":
|
|
173
|
+
return f"(NOT {self.operands[0]})"
|
|
174
|
+
return f"({' ' + self.op + ' '.join(str(op) for op in self.operands)})"
|
|
175
|
+
|
|
176
|
+
|
|
177
|
+
class SQLFunction(SQLExpression):
|
|
178
|
+
"""SQL 函数调用表达式"""
|
|
179
|
+
|
|
180
|
+
def __init__(self, name: str, *args: SQLExpression, **kwargs: SQLExpression):
|
|
181
|
+
self.name = name
|
|
182
|
+
self.args = args
|
|
183
|
+
self.kwargs = kwargs
|
|
184
|
+
|
|
185
|
+
def to_sql(self, dialect) -> str:
|
|
186
|
+
args_sql = [arg.to_sql(dialect) for arg in self.args]
|
|
187
|
+
kwargs_sql = [f"{k}={v.to_sql(dialect)}" for k, v in self.kwargs.items()]
|
|
188
|
+
all_args = ", ".join(args_sql + kwargs_sql)
|
|
189
|
+
return f"{self.name}({all_args})"
|
|
190
|
+
|
|
191
|
+
def __repr__(self) -> str:
|
|
192
|
+
args_str = ", ".join(repr(a) for a in self.args)
|
|
193
|
+
return f"{self.name}({args_str})"
|
|
194
|
+
|
|
195
|
+
|
|
196
|
+
class SQLCase(SQLExpression):
|
|
197
|
+
"""CASE WHEN 表达式"""
|
|
198
|
+
|
|
199
|
+
def __init__(
|
|
200
|
+
self,
|
|
201
|
+
when_clauses: List[Tuple[SQLExpression, SQLExpression]],
|
|
202
|
+
else_: Optional[SQLExpression] = None,
|
|
203
|
+
):
|
|
204
|
+
self.when_clauses = when_clauses
|
|
205
|
+
self.else_ = else_
|
|
206
|
+
|
|
207
|
+
def to_sql(self, dialect) -> str:
|
|
208
|
+
when_sql = [(cond.to_sql(dialect), val.to_sql(dialect)) for cond, val in self.when_clauses]
|
|
209
|
+
else_sql = self.else_.to_sql(dialect) if self.else_ else None
|
|
210
|
+
return dialect.func_case(when_sql, else_sql)
|
|
211
|
+
|
|
212
|
+
def __repr__(self) -> str:
|
|
213
|
+
else_str = f" ELSE {self.else_}" if self.else_ else ""
|
|
214
|
+
when_str = " ".join(f"WHEN {cond} THEN {val}" for cond, val in self.when_clauses)
|
|
215
|
+
return f"CASE {when_str}{else_str} END"
|
|
216
|
+
|
|
217
|
+
|
|
218
|
+
def wrap_sql_expr(value: Any) -> SQLExpression:
|
|
219
|
+
"""将值包装为 SQL 表达式"""
|
|
220
|
+
if isinstance(value, SQLExpression):
|
|
221
|
+
return value
|
|
222
|
+
if isinstance(value, str):
|
|
223
|
+
return ColumnRef(value)
|
|
224
|
+
return LiteralValue(value)
|
|
225
|
+
|
|
226
|
+
|
|
227
|
+
def col(name: str, table: Optional[str] = None) -> ColumnRef:
|
|
228
|
+
"""创建列引用"""
|
|
229
|
+
return ColumnRef(name, table)
|
|
230
|
+
|
|
231
|
+
|
|
232
|
+
def lit(value: Any) -> LiteralValue:
|
|
233
|
+
"""创建字面量"""
|
|
234
|
+
return LiteralValue(value)
|
|
@@ -0,0 +1,433 @@
|
|
|
1
|
+
# coding=utf-8
|
|
2
|
+
"""
|
|
3
|
+
符号计算引擎 - 技术指标函数库
|
|
4
|
+
|
|
5
|
+
提供常用的技术分析指标函数。
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from __future__ import annotations
|
|
9
|
+
|
|
10
|
+
from typing import TYPE_CHECKING
|
|
11
|
+
|
|
12
|
+
if TYPE_CHECKING:
|
|
13
|
+
from QuantNodes.symbolic.expression import SQLExpression
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
class TechnicalFunctions:
|
|
17
|
+
"""
|
|
18
|
+
技术分析函数库
|
|
19
|
+
|
|
20
|
+
提供常用的技术指标函数,如移动平均、RSI、MACD 等。
|
|
21
|
+
这些函数生成 SQL 表达式,可在不同数据库方言中执行。
|
|
22
|
+
"""
|
|
23
|
+
|
|
24
|
+
@staticmethod
|
|
25
|
+
def sma(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
26
|
+
"""
|
|
27
|
+
简单移动平均
|
|
28
|
+
|
|
29
|
+
Args:
|
|
30
|
+
expr: 表达式
|
|
31
|
+
window: 窗口大小
|
|
32
|
+
|
|
33
|
+
Returns:
|
|
34
|
+
SQLExpression
|
|
35
|
+
"""
|
|
36
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
37
|
+
return SQLFunction("avg", expr)
|
|
38
|
+
|
|
39
|
+
@staticmethod
|
|
40
|
+
def ema(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
41
|
+
"""
|
|
42
|
+
指数移动平均
|
|
43
|
+
|
|
44
|
+
Args:
|
|
45
|
+
expr: 表达式
|
|
46
|
+
window: 窗口大小
|
|
47
|
+
|
|
48
|
+
Returns:
|
|
49
|
+
SQLExpression
|
|
50
|
+
"""
|
|
51
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
52
|
+
return SQLFunction("expAverage", expr)
|
|
53
|
+
|
|
54
|
+
@staticmethod
|
|
55
|
+
def sum(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
56
|
+
"""
|
|
57
|
+
滑动窗口求和
|
|
58
|
+
|
|
59
|
+
Args:
|
|
60
|
+
expr: 表达式
|
|
61
|
+
window: 窗口大小
|
|
62
|
+
|
|
63
|
+
Returns:
|
|
64
|
+
SQLExpression
|
|
65
|
+
"""
|
|
66
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
67
|
+
return SQLFunction("sum", expr)
|
|
68
|
+
|
|
69
|
+
@staticmethod
|
|
70
|
+
def stddev(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
71
|
+
"""
|
|
72
|
+
滑动窗口标准差
|
|
73
|
+
|
|
74
|
+
Args:
|
|
75
|
+
expr: 表达式
|
|
76
|
+
window: 窗口大小
|
|
77
|
+
|
|
78
|
+
Returns:
|
|
79
|
+
SQLExpression
|
|
80
|
+
"""
|
|
81
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
82
|
+
return SQLFunction("stddevPop", expr)
|
|
83
|
+
|
|
84
|
+
@staticmethod
|
|
85
|
+
def variance(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
86
|
+
"""
|
|
87
|
+
滑动窗口方差
|
|
88
|
+
|
|
89
|
+
Args:
|
|
90
|
+
expr: 表达式
|
|
91
|
+
window: 窗口大小
|
|
92
|
+
|
|
93
|
+
Returns:
|
|
94
|
+
SQLExpression
|
|
95
|
+
"""
|
|
96
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
97
|
+
return SQLFunction("varPop", expr)
|
|
98
|
+
|
|
99
|
+
@staticmethod
|
|
100
|
+
def min(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
101
|
+
"""
|
|
102
|
+
滑动窗口最小值
|
|
103
|
+
|
|
104
|
+
Args:
|
|
105
|
+
expr: 表达式
|
|
106
|
+
window: 窗口大小
|
|
107
|
+
|
|
108
|
+
Returns:
|
|
109
|
+
SQLExpression
|
|
110
|
+
"""
|
|
111
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
112
|
+
return SQLFunction("min", expr)
|
|
113
|
+
|
|
114
|
+
@staticmethod
|
|
115
|
+
def max(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
116
|
+
"""
|
|
117
|
+
滑动窗口最大值
|
|
118
|
+
|
|
119
|
+
Args:
|
|
120
|
+
expr: 表达式
|
|
121
|
+
window: 窗口大小
|
|
122
|
+
|
|
123
|
+
Returns:
|
|
124
|
+
SQLExpression
|
|
125
|
+
"""
|
|
126
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
127
|
+
return SQLFunction("max", expr)
|
|
128
|
+
|
|
129
|
+
@staticmethod
|
|
130
|
+
def median(expr: "SQLExpression", window: int) -> "SQLExpression":
|
|
131
|
+
"""
|
|
132
|
+
滑动窗口中位数
|
|
133
|
+
|
|
134
|
+
Args:
|
|
135
|
+
expr: 表达式
|
|
136
|
+
window: 窗口大小
|
|
137
|
+
|
|
138
|
+
Returns:
|
|
139
|
+
SQLExpression
|
|
140
|
+
"""
|
|
141
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
142
|
+
return SQLFunction("median", expr)
|
|
143
|
+
|
|
144
|
+
@staticmethod
|
|
145
|
+
def quantile(expr: "SQLExpression", window: int, q: float) -> "SQLExpression":
|
|
146
|
+
"""
|
|
147
|
+
滑动窗口分位数
|
|
148
|
+
|
|
149
|
+
Args:
|
|
150
|
+
expr: 表达式
|
|
151
|
+
window: 窗口大小
|
|
152
|
+
q: 分位数 (0-1)
|
|
153
|
+
|
|
154
|
+
Returns:
|
|
155
|
+
SQLExpression
|
|
156
|
+
"""
|
|
157
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
158
|
+
return SQLFunction("quantile", expr)
|
|
159
|
+
|
|
160
|
+
@staticmethod
|
|
161
|
+
def delay(expr: "SQLExpression", n: int = 1) -> "SQLExpression":
|
|
162
|
+
"""
|
|
163
|
+
滞后操作 (N日前值)
|
|
164
|
+
|
|
165
|
+
Args:
|
|
166
|
+
expr: 表达式
|
|
167
|
+
n: 滞后周期数
|
|
168
|
+
|
|
169
|
+
Returns:
|
|
170
|
+
SQLExpression
|
|
171
|
+
"""
|
|
172
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
173
|
+
return SQLFunction("lagInFrame", expr)
|
|
174
|
+
|
|
175
|
+
@staticmethod
|
|
176
|
+
def delta(expr: "SQLExpression", n: int = 1) -> "SQLExpression":
|
|
177
|
+
"""
|
|
178
|
+
差分 (与N日前的差值)
|
|
179
|
+
|
|
180
|
+
Args:
|
|
181
|
+
expr: 表达式
|
|
182
|
+
n: 滞后周期数
|
|
183
|
+
|
|
184
|
+
Returns:
|
|
185
|
+
SQLExpression
|
|
186
|
+
"""
|
|
187
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
188
|
+
current = expr
|
|
189
|
+
lagged = SQLFunction("lagInFrame", expr)
|
|
190
|
+
return current - lagged
|
|
191
|
+
|
|
192
|
+
@staticmethod
|
|
193
|
+
def pct_change(expr: "SQLExpression", n: int = 1) -> "SQLExpression":
|
|
194
|
+
"""
|
|
195
|
+
百分比变化
|
|
196
|
+
|
|
197
|
+
Args:
|
|
198
|
+
expr: 表达式
|
|
199
|
+
n: 滞后周期数
|
|
200
|
+
|
|
201
|
+
Returns:
|
|
202
|
+
SQLExpression
|
|
203
|
+
"""
|
|
204
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
205
|
+
current = expr
|
|
206
|
+
lagged = SQLFunction("lagInFrame", expr)
|
|
207
|
+
return (current - lagged) / lagged
|
|
208
|
+
|
|
209
|
+
@staticmethod
|
|
210
|
+
def correlation(x: "SQLExpression", y: "SQLExpression", window: int) -> "SQLExpression":
|
|
211
|
+
"""
|
|
212
|
+
滑动窗口相关系数
|
|
213
|
+
|
|
214
|
+
Args:
|
|
215
|
+
x: X 表达式
|
|
216
|
+
y: Y 表达式
|
|
217
|
+
window: 窗口大小
|
|
218
|
+
|
|
219
|
+
Returns:
|
|
220
|
+
SQLExpression
|
|
221
|
+
"""
|
|
222
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
223
|
+
return SQLFunction("corr", x, y)
|
|
224
|
+
|
|
225
|
+
@staticmethod
|
|
226
|
+
def covariance(x: "SQLExpression", y: "SQLExpression", window: int) -> "SQLExpression":
|
|
227
|
+
"""
|
|
228
|
+
滑动窗口协方差
|
|
229
|
+
|
|
230
|
+
Args:
|
|
231
|
+
x: X 表达式
|
|
232
|
+
y: Y 表达式
|
|
233
|
+
window: 窗口大小
|
|
234
|
+
|
|
235
|
+
Returns:
|
|
236
|
+
SQLExpression
|
|
237
|
+
"""
|
|
238
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
239
|
+
return SQLFunction("covarPop", x, y)
|
|
240
|
+
|
|
241
|
+
@staticmethod
|
|
242
|
+
def rank(expr: "SQLExpression") -> "SQLExpression":
|
|
243
|
+
"""
|
|
244
|
+
排名
|
|
245
|
+
|
|
246
|
+
Returns:
|
|
247
|
+
SQLExpression
|
|
248
|
+
"""
|
|
249
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
250
|
+
return SQLFunction("rank")
|
|
251
|
+
|
|
252
|
+
@staticmethod
|
|
253
|
+
def dense_rank(expr: "SQLExpression") -> "SQLExpression":
|
|
254
|
+
"""
|
|
255
|
+
密集排名
|
|
256
|
+
|
|
257
|
+
Returns:
|
|
258
|
+
SQLExpression
|
|
259
|
+
"""
|
|
260
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
261
|
+
return SQLFunction("dense_rank")
|
|
262
|
+
|
|
263
|
+
@staticmethod
|
|
264
|
+
def row_number(expr: "SQLExpression") -> "SQLExpression":
|
|
265
|
+
"""
|
|
266
|
+
行号
|
|
267
|
+
|
|
268
|
+
Returns:
|
|
269
|
+
SQLExpression
|
|
270
|
+
"""
|
|
271
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
272
|
+
return SQLFunction("row_number")
|
|
273
|
+
|
|
274
|
+
@staticmethod
|
|
275
|
+
def cumsum(expr: "SQLExpression") -> "SQLExpression":
|
|
276
|
+
"""
|
|
277
|
+
累积求和
|
|
278
|
+
|
|
279
|
+
Returns:
|
|
280
|
+
SQLExpression
|
|
281
|
+
"""
|
|
282
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
283
|
+
return SQLFunction("sum", expr)
|
|
284
|
+
|
|
285
|
+
@staticmethod
|
|
286
|
+
def cumprod(expr: "SQLExpression") -> "SQLExpression":
|
|
287
|
+
"""
|
|
288
|
+
累积求积
|
|
289
|
+
|
|
290
|
+
Returns:
|
|
291
|
+
SQLExpression
|
|
292
|
+
"""
|
|
293
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
294
|
+
return SQLFunction("groupArray", expr)
|
|
295
|
+
|
|
296
|
+
@staticmethod
|
|
297
|
+
def running_diff(expr: "SQLExpression") -> "SQLExpression":
|
|
298
|
+
"""
|
|
299
|
+
行间差分
|
|
300
|
+
|
|
301
|
+
Returns:
|
|
302
|
+
SQLExpression
|
|
303
|
+
"""
|
|
304
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
305
|
+
return SQLFunction("runningDifference", expr)
|
|
306
|
+
|
|
307
|
+
@staticmethod
|
|
308
|
+
def abs(expr: "SQLExpression") -> "SQLExpression":
|
|
309
|
+
"""
|
|
310
|
+
绝对值
|
|
311
|
+
|
|
312
|
+
Returns:
|
|
313
|
+
SQLExpression
|
|
314
|
+
"""
|
|
315
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
316
|
+
return SQLFunction("abs", expr)
|
|
317
|
+
|
|
318
|
+
@staticmethod
|
|
319
|
+
def sqrt(expr: "SQLExpression") -> "SQLExpression":
|
|
320
|
+
"""
|
|
321
|
+
平方根
|
|
322
|
+
|
|
323
|
+
Returns:
|
|
324
|
+
SQLExpression
|
|
325
|
+
"""
|
|
326
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
327
|
+
return SQLFunction("sqrt", expr)
|
|
328
|
+
|
|
329
|
+
@staticmethod
|
|
330
|
+
def log(expr: "SQLExpression") -> "SQLExpression":
|
|
331
|
+
"""
|
|
332
|
+
自然对数
|
|
333
|
+
|
|
334
|
+
Returns:
|
|
335
|
+
SQLExpression
|
|
336
|
+
"""
|
|
337
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
338
|
+
return SQLFunction("log", expr)
|
|
339
|
+
|
|
340
|
+
@staticmethod
|
|
341
|
+
def log10(expr: "SQLExpression") -> "SQLExpression":
|
|
342
|
+
"""
|
|
343
|
+
底数为10的对数
|
|
344
|
+
|
|
345
|
+
Returns:
|
|
346
|
+
SQLExpression
|
|
347
|
+
"""
|
|
348
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
349
|
+
return SQLFunction("log10", expr)
|
|
350
|
+
|
|
351
|
+
@staticmethod
|
|
352
|
+
def pow(expr: "SQLExpression", power: float) -> "SQLExpression":
|
|
353
|
+
"""
|
|
354
|
+
幂函数
|
|
355
|
+
|
|
356
|
+
Args:
|
|
357
|
+
expr: 表达式
|
|
358
|
+
power: 幂次
|
|
359
|
+
|
|
360
|
+
Returns:
|
|
361
|
+
SQLExpression
|
|
362
|
+
"""
|
|
363
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
364
|
+
return SQLFunction("pow", expr)
|
|
365
|
+
|
|
366
|
+
@staticmethod
|
|
367
|
+
def round(expr: "SQLExpression", decimals: int = 0) -> "SQLExpression":
|
|
368
|
+
"""
|
|
369
|
+
四舍五入
|
|
370
|
+
|
|
371
|
+
Args:
|
|
372
|
+
expr: 表达式
|
|
373
|
+
decimals: 小数位数
|
|
374
|
+
|
|
375
|
+
Returns:
|
|
376
|
+
SQLExpression
|
|
377
|
+
"""
|
|
378
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
379
|
+
return SQLFunction("round", expr)
|
|
380
|
+
|
|
381
|
+
@staticmethod
|
|
382
|
+
def ceil(expr: "SQLExpression") -> "SQLExpression":
|
|
383
|
+
"""
|
|
384
|
+
向上取整
|
|
385
|
+
|
|
386
|
+
Returns:
|
|
387
|
+
SQLExpression
|
|
388
|
+
"""
|
|
389
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
390
|
+
return SQLFunction("ceil", expr)
|
|
391
|
+
|
|
392
|
+
@staticmethod
|
|
393
|
+
def floor(expr: "SQLExpression") -> "SQLExpression":
|
|
394
|
+
"""
|
|
395
|
+
向下取整
|
|
396
|
+
|
|
397
|
+
Returns:
|
|
398
|
+
SQLExpression
|
|
399
|
+
"""
|
|
400
|
+
from QuantNodes.symbolic.expression import SQLFunction
|
|
401
|
+
return SQLFunction("floor", expr)
|
|
402
|
+
|
|
403
|
+
|
|
404
|
+
TA_FUNCTIONS = {
|
|
405
|
+
"sma": TechnicalFunctions.sma,
|
|
406
|
+
"ema": TechnicalFunctions.ema,
|
|
407
|
+
"sum": TechnicalFunctions.sum,
|
|
408
|
+
"stddev": TechnicalFunctions.stddev,
|
|
409
|
+
"variance": TechnicalFunctions.variance,
|
|
410
|
+
"min": TechnicalFunctions.min,
|
|
411
|
+
"max": TechnicalFunctions.max,
|
|
412
|
+
"median": TechnicalFunctions.median,
|
|
413
|
+
"quantile": TechnicalFunctions.quantile,
|
|
414
|
+
"delay": TechnicalFunctions.delay,
|
|
415
|
+
"delta": TechnicalFunctions.delta,
|
|
416
|
+
"pct_change": TechnicalFunctions.pct_change,
|
|
417
|
+
"correlation": TechnicalFunctions.correlation,
|
|
418
|
+
"covariance": TechnicalFunctions.covariance,
|
|
419
|
+
"rank": TechnicalFunctions.rank,
|
|
420
|
+
"dense_rank": TechnicalFunctions.dense_rank,
|
|
421
|
+
"row_number": TechnicalFunctions.row_number,
|
|
422
|
+
"cumsum": TechnicalFunctions.cumsum,
|
|
423
|
+
"cumprod": TechnicalFunctions.cumprod,
|
|
424
|
+
"running_diff": TechnicalFunctions.running_diff,
|
|
425
|
+
"abs": TechnicalFunctions.abs,
|
|
426
|
+
"sqrt": TechnicalFunctions.sqrt,
|
|
427
|
+
"log": TechnicalFunctions.log,
|
|
428
|
+
"log10": TechnicalFunctions.log10,
|
|
429
|
+
"pow": TechnicalFunctions.pow,
|
|
430
|
+
"round": TechnicalFunctions.round,
|
|
431
|
+
"ceil": TechnicalFunctions.ceil,
|
|
432
|
+
"floor": TechnicalFunctions.floor,
|
|
433
|
+
}
|