aigroup-econ-mcp 1.3.3__py3-none-any.whl → 2.0.1__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.
Files changed (198) hide show
  1. .gitignore +253 -0
  2. PKG-INFO +732 -0
  3. README.md +687 -0
  4. __init__.py +14 -0
  5. aigroup_econ_mcp-2.0.1.dist-info/METADATA +732 -0
  6. aigroup_econ_mcp-2.0.1.dist-info/RECORD +170 -0
  7. aigroup_econ_mcp-2.0.1.dist-info/entry_points.txt +2 -0
  8. aigroup_econ_mcp-2.0.1.dist-info/licenses/LICENSE +21 -0
  9. cli.py +32 -0
  10. econometrics/README.md +18 -0
  11. econometrics/__init__.py +191 -0
  12. econometrics/advanced_methods/modern_computing_machine_learning/__init__.py +30 -0
  13. econometrics/advanced_methods/modern_computing_machine_learning/causal_forest.py +253 -0
  14. econometrics/advanced_methods/modern_computing_machine_learning/double_ml.py +268 -0
  15. econometrics/advanced_methods/modern_computing_machine_learning/gradient_boosting.py +249 -0
  16. econometrics/advanced_methods/modern_computing_machine_learning/hierarchical_clustering.py +243 -0
  17. econometrics/advanced_methods/modern_computing_machine_learning/kmeans_clustering.py +293 -0
  18. econometrics/advanced_methods/modern_computing_machine_learning/neural_network.py +264 -0
  19. econometrics/advanced_methods/modern_computing_machine_learning/random_forest.py +195 -0
  20. econometrics/advanced_methods/modern_computing_machine_learning/support_vector_machine.py +226 -0
  21. econometrics/advanced_methods/modern_computing_machine_learning/test_all_modules.py +329 -0
  22. econometrics/advanced_methods/modern_computing_machine_learning/test_report.md +107 -0
  23. econometrics/basic_parametric_estimation/__init__.py +31 -0
  24. econometrics/basic_parametric_estimation/gmm/__init__.py +13 -0
  25. econometrics/basic_parametric_estimation/gmm/gmm_model.py +256 -0
  26. econometrics/basic_parametric_estimation/mle/__init__.py +13 -0
  27. econometrics/basic_parametric_estimation/mle/mle_model.py +241 -0
  28. econometrics/basic_parametric_estimation/ols/__init__.py +13 -0
  29. econometrics/basic_parametric_estimation/ols/ols_model.py +141 -0
  30. econometrics/causal_inference/__init__.py +66 -0
  31. econometrics/causal_inference/causal_identification_strategy/__init__.py +104 -0
  32. econometrics/causal_inference/causal_identification_strategy/control_function.py +112 -0
  33. econometrics/causal_inference/causal_identification_strategy/difference_in_differences.py +107 -0
  34. econometrics/causal_inference/causal_identification_strategy/event_study.py +119 -0
  35. econometrics/causal_inference/causal_identification_strategy/first_difference.py +89 -0
  36. econometrics/causal_inference/causal_identification_strategy/fixed_effects.py +103 -0
  37. econometrics/causal_inference/causal_identification_strategy/hausman_test.py +69 -0
  38. econometrics/causal_inference/causal_identification_strategy/instrumental_variables.py +145 -0
  39. econometrics/causal_inference/causal_identification_strategy/mediation_analysis.py +121 -0
  40. econometrics/causal_inference/causal_identification_strategy/moderation_analysis.py +109 -0
  41. econometrics/causal_inference/causal_identification_strategy/propensity_score_matching.py +140 -0
  42. econometrics/causal_inference/causal_identification_strategy/random_effects.py +100 -0
  43. econometrics/causal_inference/causal_identification_strategy/regression_discontinuity.py +98 -0
  44. econometrics/causal_inference/causal_identification_strategy/synthetic_control.py +111 -0
  45. econometrics/causal_inference/causal_identification_strategy/triple_difference.py +86 -0
  46. econometrics/distribution_analysis/__init__.py +28 -0
  47. econometrics/distribution_analysis/oaxaca_blinder.py +184 -0
  48. econometrics/distribution_analysis/time_series_decomposition.py +152 -0
  49. econometrics/distribution_analysis/variance_decomposition.py +179 -0
  50. econometrics/missing_data/__init__.py +18 -0
  51. econometrics/missing_data/imputation_methods.py +219 -0
  52. econometrics/missing_data/missing_data_measurement_error/__init__.py +0 -0
  53. econometrics/model_specification_diagnostics_robust_inference/README.md +173 -0
  54. econometrics/model_specification_diagnostics_robust_inference/__init__.py +78 -0
  55. econometrics/model_specification_diagnostics_robust_inference/diagnostic_tests/__init__.py +20 -0
  56. econometrics/model_specification_diagnostics_robust_inference/diagnostic_tests/diagnostic_tests_model.py +149 -0
  57. econometrics/model_specification_diagnostics_robust_inference/generalized_least_squares/__init__.py +15 -0
  58. econometrics/model_specification_diagnostics_robust_inference/generalized_least_squares/gls_model.py +130 -0
  59. econometrics/model_specification_diagnostics_robust_inference/model_selection/__init__.py +18 -0
  60. econometrics/model_specification_diagnostics_robust_inference/model_selection/model_selection_model.py +286 -0
  61. econometrics/model_specification_diagnostics_robust_inference/regularization/__init__.py +15 -0
  62. econometrics/model_specification_diagnostics_robust_inference/regularization/regularization_model.py +177 -0
  63. econometrics/model_specification_diagnostics_robust_inference/robust_errors/__init__.py +15 -0
  64. econometrics/model_specification_diagnostics_robust_inference/robust_errors/robust_errors_model.py +122 -0
  65. econometrics/model_specification_diagnostics_robust_inference/simultaneous_equations/__init__.py +15 -0
  66. econometrics/model_specification_diagnostics_robust_inference/simultaneous_equations/simultaneous_equations_model.py +246 -0
  67. econometrics/model_specification_diagnostics_robust_inference/weighted_least_squares/__init__.py +15 -0
  68. econometrics/model_specification_diagnostics_robust_inference/weighted_least_squares/wls_model.py +127 -0
  69. econometrics/nonparametric/__init__.py +35 -0
  70. econometrics/nonparametric/gam_model.py +117 -0
  71. econometrics/nonparametric/kernel_regression.py +161 -0
  72. econometrics/nonparametric/nonparametric_semiparametric_methods/__init__.py +0 -0
  73. econometrics/nonparametric/quantile_regression.py +249 -0
  74. econometrics/nonparametric/spline_regression.py +100 -0
  75. econometrics/spatial_econometrics/__init__.py +68 -0
  76. econometrics/spatial_econometrics/geographically_weighted_regression.py +211 -0
  77. econometrics/spatial_econometrics/gwr_simple.py +154 -0
  78. econometrics/spatial_econometrics/spatial_autocorrelation.py +356 -0
  79. econometrics/spatial_econometrics/spatial_durbin_model.py +177 -0
  80. econometrics/spatial_econometrics/spatial_econometrics_new/__init__.py +0 -0
  81. econometrics/spatial_econometrics/spatial_regression.py +315 -0
  82. econometrics/spatial_econometrics/spatial_weights.py +226 -0
  83. econometrics/specific_data_modeling/micro_discrete_limited_data/README.md +164 -0
  84. econometrics/specific_data_modeling/micro_discrete_limited_data/__init__.py +40 -0
  85. econometrics/specific_data_modeling/micro_discrete_limited_data/count_data_models.py +311 -0
  86. econometrics/specific_data_modeling/micro_discrete_limited_data/discrete_choice_models.py +294 -0
  87. econometrics/specific_data_modeling/micro_discrete_limited_data/limited_dependent_variable_models.py +282 -0
  88. econometrics/specific_data_modeling/survival_duration_data/__init__.py +0 -0
  89. econometrics/specific_data_modeling/time_series_panel_data/__init__.py +143 -0
  90. econometrics/specific_data_modeling/time_series_panel_data/arima_model.py +104 -0
  91. econometrics/specific_data_modeling/time_series_panel_data/cointegration_vecm.py +334 -0
  92. econometrics/specific_data_modeling/time_series_panel_data/dynamic_panel_models.py +653 -0
  93. econometrics/specific_data_modeling/time_series_panel_data/exponential_smoothing.py +176 -0
  94. econometrics/specific_data_modeling/time_series_panel_data/garch_model.py +198 -0
  95. econometrics/specific_data_modeling/time_series_panel_data/panel_diagnostics.py +125 -0
  96. econometrics/specific_data_modeling/time_series_panel_data/panel_var.py +60 -0
  97. econometrics/specific_data_modeling/time_series_panel_data/structural_break_tests.py +87 -0
  98. econometrics/specific_data_modeling/time_series_panel_data/time_varying_parameter_models.py +106 -0
  99. econometrics/specific_data_modeling/time_series_panel_data/unit_root_tests.py +204 -0
  100. econometrics/specific_data_modeling/time_series_panel_data/var_svar_model.py +372 -0
  101. econometrics/statistical_inference/__init__.py +21 -0
  102. econometrics/statistical_inference/bootstrap_methods.py +162 -0
  103. econometrics/statistical_inference/permutation_test.py +177 -0
  104. econometrics/statistical_inference/statistical_inference_techniques/__init__.py +0 -0
  105. econometrics/statistics/distribution_decomposition_methods/__init__.py +0 -0
  106. econometrics/survival_analysis/__init__.py +18 -0
  107. econometrics/survival_analysis/survival_models.py +259 -0
  108. econometrics/tests/basic_parametric_estimation_tests/__init__.py +3 -0
  109. econometrics/tests/basic_parametric_estimation_tests/test_gmm.py +128 -0
  110. econometrics/tests/basic_parametric_estimation_tests/test_mle.py +127 -0
  111. econometrics/tests/basic_parametric_estimation_tests/test_ols.py +100 -0
  112. econometrics/tests/causal_inference_tests/__init__.py +3 -0
  113. econometrics/tests/causal_inference_tests/detailed_test.py +441 -0
  114. econometrics/tests/causal_inference_tests/test_all_methods.py +418 -0
  115. econometrics/tests/causal_inference_tests/test_causal_identification_strategy.py +202 -0
  116. econometrics/tests/causal_inference_tests/test_difference_in_differences.py +53 -0
  117. econometrics/tests/causal_inference_tests/test_instrumental_variables.py +44 -0
  118. econometrics/tests/model_specification_diagnostics_tests/__init__.py +3 -0
  119. econometrics/tests/model_specification_diagnostics_tests/test_diagnostic_tests.py +86 -0
  120. econometrics/tests/model_specification_diagnostics_tests/test_robust_errors.py +89 -0
  121. econometrics/tests/specific_data_modeling_tests/__init__.py +3 -0
  122. econometrics/tests/specific_data_modeling_tests/test_arima.py +98 -0
  123. econometrics/tests/specific_data_modeling_tests/test_dynamic_panel.py +198 -0
  124. econometrics/tests/specific_data_modeling_tests/test_exponential_smoothing.py +105 -0
  125. econometrics/tests/specific_data_modeling_tests/test_garch.py +118 -0
  126. econometrics/tests/specific_data_modeling_tests/test_micro_discrete_limited_data.py +189 -0
  127. econometrics/tests/specific_data_modeling_tests/test_unit_root.py +156 -0
  128. econometrics/tests/specific_data_modeling_tests/test_var.py +124 -0
  129. econometrics//321/206/320/254/320/272/321/205/342/225/235/320/220/321/205/320/237/320/241/321/205/320/264/320/267/321/207/342/226/222/342/225/227/321/204/342/225/235/320/250/321/205/320/225/320/230/321/207/342/225/221/320/267/321/205/320/230/320/226/321/206/320/256/320/240.md +544 -0
  130. prompts/__init__.py +0 -0
  131. prompts/analysis_guides.py +43 -0
  132. pyproject.toml +85 -0
  133. resources/MCP_MASTER_GUIDE.md +422 -0
  134. resources/MCP_TOOLS_DATA_FORMAT_GUIDE.md +185 -0
  135. resources/__init__.py +0 -0
  136. server.py +97 -0
  137. tools/README.md +88 -0
  138. tools/__init__.py +119 -0
  139. tools/causal_inference_adapter.py +658 -0
  140. tools/data_loader.py +213 -0
  141. tools/decorators.py +38 -0
  142. tools/distribution_analysis_adapter.py +121 -0
  143. tools/econometrics_adapter.py +286 -0
  144. tools/gwr_simple_adapter.py +54 -0
  145. tools/machine_learning_adapter.py +567 -0
  146. tools/mcp_tool_groups/__init__.py +15 -0
  147. tools/mcp_tool_groups/basic_parametric_tools.py +173 -0
  148. tools/mcp_tool_groups/causal_inference_tools.py +643 -0
  149. tools/mcp_tool_groups/distribution_analysis_tools.py +169 -0
  150. tools/mcp_tool_groups/machine_learning_tools.py +422 -0
  151. tools/mcp_tool_groups/microecon_tools.py +325 -0
  152. tools/mcp_tool_groups/missing_data_tools.py +117 -0
  153. tools/mcp_tool_groups/model_specification_tools.py +402 -0
  154. tools/mcp_tool_groups/nonparametric_tools.py +225 -0
  155. tools/mcp_tool_groups/spatial_econometrics_tools.py +323 -0
  156. tools/mcp_tool_groups/statistical_inference_tools.py +131 -0
  157. tools/mcp_tool_groups/time_series_tools.py +494 -0
  158. tools/mcp_tools_registry.py +124 -0
  159. tools/microecon_adapter.py +412 -0
  160. tools/missing_data_adapter.py +73 -0
  161. tools/model_specification_adapter.py +369 -0
  162. tools/nonparametric_adapter.py +190 -0
  163. tools/output_formatter.py +563 -0
  164. tools/spatial_econometrics_adapter.py +318 -0
  165. tools/statistical_inference_adapter.py +90 -0
  166. tools/survival_analysis_adapter.py +46 -0
  167. tools/time_series_panel_data_adapter.py +858 -0
  168. tools/time_series_panel_data_tools.py +65 -0
  169. aigroup_econ_mcp/__init__.py +0 -19
  170. aigroup_econ_mcp/cli.py +0 -82
  171. aigroup_econ_mcp/config.py +0 -561
  172. aigroup_econ_mcp/server.py +0 -452
  173. aigroup_econ_mcp/tools/__init__.py +0 -19
  174. aigroup_econ_mcp/tools/base.py +0 -470
  175. aigroup_econ_mcp/tools/cache.py +0 -533
  176. aigroup_econ_mcp/tools/data_loader.py +0 -195
  177. aigroup_econ_mcp/tools/file_parser.py +0 -1027
  178. aigroup_econ_mcp/tools/machine_learning.py +0 -60
  179. aigroup_econ_mcp/tools/ml_ensemble.py +0 -210
  180. aigroup_econ_mcp/tools/ml_evaluation.py +0 -272
  181. aigroup_econ_mcp/tools/ml_models.py +0 -54
  182. aigroup_econ_mcp/tools/ml_regularization.py +0 -186
  183. aigroup_econ_mcp/tools/monitoring.py +0 -555
  184. aigroup_econ_mcp/tools/optimized_example.py +0 -229
  185. aigroup_econ_mcp/tools/panel_data.py +0 -619
  186. aigroup_econ_mcp/tools/regression.py +0 -214
  187. aigroup_econ_mcp/tools/statistics.py +0 -154
  188. aigroup_econ_mcp/tools/time_series.py +0 -698
  189. aigroup_econ_mcp/tools/timeout.py +0 -283
  190. aigroup_econ_mcp/tools/tool_descriptions.py +0 -410
  191. aigroup_econ_mcp/tools/tool_handlers.py +0 -1016
  192. aigroup_econ_mcp/tools/tool_registry.py +0 -478
  193. aigroup_econ_mcp/tools/validation.py +0 -482
  194. aigroup_econ_mcp-1.3.3.dist-info/METADATA +0 -525
  195. aigroup_econ_mcp-1.3.3.dist-info/RECORD +0 -30
  196. aigroup_econ_mcp-1.3.3.dist-info/entry_points.txt +0 -2
  197. /aigroup_econ_mcp-1.3.3.dist-info/licenses/LICENSE → /LICENSE +0 -0
  198. {aigroup_econ_mcp-1.3.3.dist-info → aigroup_econ_mcp-2.0.1.dist-info}/WHEEL +0 -0
tools/data_loader.py ADDED
@@ -0,0 +1,213 @@
1
+ """
2
+ 数据加载组件 - 支持多种文件格式
3
+ 支持txt、json、csv、excel文件的读取和解析
4
+ """
5
+
6
+ import json
7
+ from pathlib import Path
8
+ from typing import Any, Dict, List, Union
9
+ import pandas as pd
10
+
11
+
12
+ class DataLoader:
13
+ """数据加载器,支持多种文件格式"""
14
+
15
+ @staticmethod
16
+ def load_from_file(file_path: str) -> Dict[str, Any]:
17
+ """
18
+ 从文件加载数据
19
+
20
+ Args:
21
+ file_path: 文件路径
22
+
23
+ Returns:
24
+ 包含y_data和x_data的字典
25
+
26
+ Raises:
27
+ FileNotFoundError: 文件不存在
28
+ ValueError: 不支持的文件格式或数据格式错误
29
+ """
30
+ path = Path(file_path)
31
+
32
+ if not path.exists():
33
+ raise FileNotFoundError(f"文件不存在: {file_path}")
34
+
35
+ suffix = path.suffix.lower()
36
+
37
+ if suffix == '.txt':
38
+ return DataLoader._load_txt(path)
39
+ elif suffix == '.json':
40
+ return DataLoader._load_json(path)
41
+ elif suffix == '.csv':
42
+ return DataLoader._load_csv(path)
43
+ elif suffix in ['.xlsx', '.xls']:
44
+ return DataLoader._load_excel(path)
45
+ else:
46
+ raise ValueError(f"不支持的文件格式: {suffix}")
47
+
48
+ @staticmethod
49
+ def _load_txt(path: Path) -> Dict[str, Any]:
50
+ """加载txt文件(空格或制表符分隔)"""
51
+ with open(path, 'r', encoding='utf-8') as f:
52
+ lines = f.readlines()
53
+
54
+ # 跳过空行和注释行
55
+ data_lines = [line.strip() for line in lines if line.strip() and not line.strip().startswith('#')]
56
+
57
+ if not data_lines:
58
+ raise ValueError("txt文件为空或没有有效数据")
59
+
60
+ # 解析数据
61
+ data = []
62
+ for line in data_lines:
63
+ # 支持空格和制表符分隔
64
+ row = [float(x) for x in line.split()]
65
+ data.append(row)
66
+
67
+ return DataLoader._parse_data_matrix(data)
68
+
69
+ @staticmethod
70
+ def _load_json(path: Path) -> Dict[str, Any]:
71
+ """加载json文件"""
72
+ with open(path, 'r', encoding='utf-8') as f:
73
+ data = json.load(f)
74
+
75
+ # 支持两种格式:
76
+ # 1. {"y_data": [...], "x_data": [[...], ...]}
77
+ # 2. {"data": [[y, x1, x2, ...], ...]}
78
+
79
+ if "y_data" in data and "x_data" in data:
80
+ return {
81
+ "y_data": data["y_data"],
82
+ "x_data": data["x_data"],
83
+ "feature_names": data.get("feature_names"),
84
+ }
85
+ elif "data" in data:
86
+ return DataLoader._parse_data_matrix(data["data"])
87
+ else:
88
+ raise ValueError("JSON格式错误:需要包含'y_data'和'x_data'或'data'字段")
89
+
90
+ @staticmethod
91
+ def _load_csv(path: Path) -> Dict[str, Any]:
92
+ """加载csv文件"""
93
+ df = pd.read_csv(path)
94
+ return DataLoader._parse_dataframe(df)
95
+
96
+ @staticmethod
97
+ def _load_excel(path: Path) -> Dict[str, Any]:
98
+ """加载excel文件"""
99
+ df = pd.read_excel(path)
100
+ return DataLoader._parse_dataframe(df)
101
+
102
+ @staticmethod
103
+ def _parse_dataframe(df: pd.DataFrame) -> Dict[str, Any]:
104
+ """解析DataFrame"""
105
+ if df.empty:
106
+ raise ValueError("数据框为空")
107
+
108
+ # 第一列为y,其余列为x
109
+ y_data = df.iloc[:, 0].tolist()
110
+
111
+ if df.shape[1] > 1:
112
+ x_data = df.iloc[:, 1:].values.tolist()
113
+ feature_names = df.columns[1:].tolist()
114
+ else:
115
+ raise ValueError("数据至少需要包含因变量和一个自变量")
116
+
117
+ return {
118
+ "y_data": y_data,
119
+ "x_data": x_data,
120
+ "feature_names": feature_names,
121
+ }
122
+
123
+ @staticmethod
124
+ def _parse_data_matrix(data: List[List[float]]) -> Dict[str, Any]:
125
+ """解析数据矩阵(第一列为y,其余列为x)"""
126
+ if not data:
127
+ raise ValueError("数据矩阵为空")
128
+
129
+ y_data = [row[0] for row in data]
130
+
131
+ if len(data[0]) > 1:
132
+ x_data = [row[1:] for row in data]
133
+ feature_names = [f"X{i+1}" for i in range(len(data[0]) - 1)]
134
+ else:
135
+ raise ValueError("数据至少需要包含因变量和一个自变量")
136
+
137
+ return {
138
+ "y_data": y_data,
139
+ "x_data": x_data,
140
+ "feature_names": feature_names,
141
+ }
142
+
143
+
144
+ class MLEDataLoader:
145
+ """MLE专用数据加载器"""
146
+
147
+ @staticmethod
148
+ def load_from_file(file_path: str) -> Dict[str, Any]:
149
+ """
150
+ 从文件加载MLE数据(单列数据)
151
+
152
+ Args:
153
+ file_path: 文件路径
154
+
155
+ Returns:
156
+ 包含data的字典
157
+ """
158
+ path = Path(file_path)
159
+
160
+ if not path.exists():
161
+ raise FileNotFoundError(f"文件不存在: {file_path}")
162
+
163
+ suffix = path.suffix.lower()
164
+
165
+ if suffix == '.txt':
166
+ return MLEDataLoader._load_txt(path)
167
+ elif suffix == '.json':
168
+ return MLEDataLoader._load_json(path)
169
+ elif suffix == '.csv':
170
+ return MLEDataLoader._load_csv(path)
171
+ elif suffix in ['.xlsx', '.xls']:
172
+ return MLEDataLoader._load_excel(path)
173
+ else:
174
+ raise ValueError(f"不支持的文件格式: {suffix}")
175
+
176
+ @staticmethod
177
+ def _load_txt(path: Path) -> Dict[str, Any]:
178
+ """加载txt文件"""
179
+ with open(path, 'r', encoding='utf-8') as f:
180
+ lines = f.readlines()
181
+
182
+ data = []
183
+ for line in lines:
184
+ line = line.strip()
185
+ if line and not line.startswith('#'):
186
+ data.append(float(line.split()[0]))
187
+
188
+ return {"data": data}
189
+
190
+ @staticmethod
191
+ def _load_json(path: Path) -> Dict[str, Any]:
192
+ """加载json文件"""
193
+ with open(path, 'r', encoding='utf-8') as f:
194
+ loaded = json.load(f)
195
+
196
+ if isinstance(loaded, dict) and "data" in loaded:
197
+ return {"data": loaded["data"]}
198
+ elif isinstance(loaded, list):
199
+ return {"data": loaded}
200
+ else:
201
+ raise ValueError("JSON格式错误")
202
+
203
+ @staticmethod
204
+ def _load_csv(path: Path) -> Dict[str, Any]:
205
+ """加载csv文件"""
206
+ df = pd.read_csv(path)
207
+ return {"data": df.iloc[:, 0].tolist()}
208
+
209
+ @staticmethod
210
+ def _load_excel(path: Path) -> Dict[str, Any]:
211
+ """加载excel文件"""
212
+ df = pd.read_excel(path)
213
+ return {"data": df.iloc[:, 0].tolist()}
tools/decorators.py ADDED
@@ -0,0 +1,38 @@
1
+ """
2
+ 工具装饰器模块
3
+ """
4
+
5
+ from functools import wraps
6
+ from typing import Callable, Any
7
+
8
+
9
+ def with_file_support_decorator(tool_name: str):
10
+ """
11
+ 支持文件输入的装饰器
12
+
13
+ Args:
14
+ tool_name: 工具名称
15
+ """
16
+ def decorator(func: Callable) -> Callable:
17
+ @wraps(func)
18
+ def wrapper(*args, **kwargs):
19
+ # 简化实现 - 直接调用原函数
20
+ return func(*args, **kwargs)
21
+ return wrapper
22
+ return decorator
23
+
24
+
25
+ def validate_input(data_type: str = "econometric"):
26
+ """
27
+ 输入验证装饰器
28
+
29
+ Args:
30
+ data_type: 数据类型
31
+ """
32
+ def decorator(func: Callable) -> Callable:
33
+ @wraps(func)
34
+ def wrapper(*args, **kwargs):
35
+ # 简化实现 - 直接调用原函数
36
+ return func(*args, **kwargs)
37
+ return wrapper
38
+ return decorator
@@ -0,0 +1,121 @@
1
+ """
2
+ 分布分析与分解方法适配器
3
+ 将核心算法适配为MCP工具
4
+ """
5
+
6
+ from typing import List, Optional
7
+ import json
8
+
9
+ from econometrics.distribution_analysis import (
10
+ oaxaca_blinder_decomposition,
11
+ variance_decomposition,
12
+ time_series_decomposition,
13
+ OaxacaResult,
14
+ VarianceDecompositionResult,
15
+ TimeSeriesDecompositionResult
16
+ )
17
+
18
+ from .output_formatter import OutputFormatter
19
+
20
+
21
+ def oaxaca_blinder_adapter(
22
+ y_a: List[float],
23
+ x_a: List[List[float]],
24
+ y_b: List[float],
25
+ x_b: List[List[float]],
26
+ feature_names: Optional[List[str]] = None,
27
+ weight_matrix: str = "pooled",
28
+ output_format: str = "json",
29
+ save_path: Optional[str] = None
30
+ ) -> str:
31
+ """Oaxaca-Blinder分解适配器"""
32
+
33
+ result: OaxacaResult = oaxaca_blinder_decomposition(
34
+ y_a=y_a,
35
+ x_a=x_a,
36
+ y_b=y_b,
37
+ x_b=x_b,
38
+ feature_names=feature_names,
39
+ weight_matrix=weight_matrix
40
+ )
41
+
42
+ if output_format == "json":
43
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
44
+ if save_path:
45
+ OutputFormatter.save_to_file(json_result, save_path)
46
+ return f"分析完成!结果已保存到: {save_path}\n\n{json_result}"
47
+ return json_result
48
+ else:
49
+ formatted = f"""# Oaxaca-Blinder分解结果
50
+
51
+ {result.summary}
52
+ """
53
+ if save_path:
54
+ OutputFormatter.save_to_file(formatted, save_path)
55
+ return formatted
56
+
57
+
58
+ def variance_decomposition_adapter(
59
+ values: List[float],
60
+ groups: List[str],
61
+ group_names: Optional[List[str]] = None,
62
+ output_format: str = "json",
63
+ save_path: Optional[str] = None
64
+ ) -> str:
65
+ """方差分解适配器"""
66
+
67
+ result: VarianceDecompositionResult = variance_decomposition(
68
+ values=values,
69
+ groups=groups,
70
+ group_names=group_names
71
+ )
72
+
73
+ if output_format == "json":
74
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
75
+ if save_path:
76
+ OutputFormatter.save_to_file(json_result, save_path)
77
+ return f"分析完成!结果已保存到: {save_path}\n\n{json_result}"
78
+ return json_result
79
+ else:
80
+ formatted = f"""# 方差分解(ANOVA)结果
81
+
82
+ {result.summary}
83
+ """
84
+ if save_path:
85
+ OutputFormatter.save_to_file(formatted, save_path)
86
+ return formatted
87
+
88
+
89
+ def time_series_decomposition_adapter(
90
+ data: List[float],
91
+ period: int = 12,
92
+ model: str = "additive",
93
+ method: str = "classical",
94
+ extrapolate_trend: str = "freq",
95
+ output_format: str = "json",
96
+ save_path: Optional[str] = None
97
+ ) -> str:
98
+ """时间序列分解适配器"""
99
+
100
+ result: TimeSeriesDecompositionResult = time_series_decomposition(
101
+ data=data,
102
+ period=period,
103
+ model=model,
104
+ method=method,
105
+ extrapolate_trend=extrapolate_trend
106
+ )
107
+
108
+ if output_format == "json":
109
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
110
+ if save_path:
111
+ OutputFormatter.save_to_file(json_result, save_path)
112
+ return f"分析完成!结果已保存到: {save_path}\n\n{json_result}"
113
+ return json_result
114
+ else:
115
+ formatted = f"""# 时间序列分解结果
116
+
117
+ {result.summary}
118
+ """
119
+ if save_path:
120
+ OutputFormatter.save_to_file(formatted, save_path)
121
+ return formatted
@@ -0,0 +1,286 @@
1
+ """
2
+ 计量经济学核心算法适配器
3
+ 复用 econometrics/ 中的核心实现,避免代码重复
4
+ """
5
+
6
+ from typing import List, Optional, Union
7
+ import sys
8
+ from pathlib import Path
9
+ import json
10
+
11
+ # 确保可以导入econometrics模块
12
+ sys.path.insert(0, str(Path(__file__).parent.parent))
13
+
14
+ # 导入核心算法实现
15
+ from econometrics.basic_parametric_estimation.ols.ols_model import (
16
+ ols_regression as core_ols_regression,
17
+ OLSResult as CoreOLSResult
18
+ )
19
+ from econometrics.basic_parametric_estimation.mle.mle_model import (
20
+ mle_estimation as core_mle_estimation,
21
+ MLEResult as CoreMLEResult
22
+ )
23
+ from econometrics.basic_parametric_estimation.gmm.gmm_model import (
24
+ gmm_estimation as core_gmm_estimation,
25
+ GMMResult as CoreGMMResult
26
+ )
27
+
28
+ # 导入数据加载和格式化组件
29
+ from .data_loader import DataLoader, MLEDataLoader
30
+ from .output_formatter import OutputFormatter
31
+
32
+
33
+ class DataValidator:
34
+ """数据验证器"""
35
+
36
+ @staticmethod
37
+ def validate_ols_gmm_data(y_data: List[float], x_data: List[List[float]], feature_names: Optional[List[str]] = None):
38
+ """验证OLS和GMM数据格式"""
39
+ if len(y_data) != len(x_data):
40
+ raise ValueError(f"因变量长度({len(y_data)})与自变量长度({len(x_data)})不一致")
41
+
42
+ # 检查所有x_data行的长度是否一致
43
+ if x_data:
44
+ first_row_len = len(x_data[0])
45
+ for i, row in enumerate(x_data):
46
+ if len(row) != first_row_len:
47
+ raise ValueError(f"自变量第{i}行长度({len(row)})与第一行长度({first_row_len})不一致")
48
+
49
+ # 验证feature_names
50
+ if feature_names and len(feature_names) != len(x_data[0]) if x_data else 0:
51
+ raise ValueError(f"特征名称数量({len(feature_names)})与自变量列数({len(x_data[0]) if x_data else 0})不一致")
52
+
53
+ @staticmethod
54
+ def convert_to_2d_list(data: Union[List[float], List[List[float]]]) -> List[List[float]]:
55
+ """将数据转换为二维列表格式"""
56
+ if not data:
57
+ return []
58
+
59
+ # 如果是一维列表,转换为二维列表
60
+ if isinstance(data[0], (int, float)):
61
+ return [[x] for x in data]
62
+
63
+ # 已经是二维列表
64
+ return data
65
+
66
+
67
+ class EconometricsAdapter:
68
+ """
69
+ 计量经济学适配器
70
+ 将core算法适配为MCP工具,支持文件输入和多种输出格式
71
+ """
72
+
73
+ @staticmethod
74
+ def ols_regression(
75
+ y_data: Optional[List[float]] = None,
76
+ x_data: Optional[List[List[float]]] = None,
77
+ file_path: Optional[str] = None,
78
+ feature_names: Optional[List[str]] = None,
79
+ constant: bool = True,
80
+ confidence_level: float = 0.95,
81
+ output_format: str = "json",
82
+ save_path: Optional[str] = None
83
+ ) -> str:
84
+ """
85
+ OLS回归适配器
86
+
87
+ 优势:复用econometrics/核心算法,避免代码重复
88
+ """
89
+ # 1. 数据准备
90
+ if file_path:
91
+ data = DataLoader.load_from_file(file_path)
92
+ y_data = data["y_data"]
93
+ x_data = data["x_data"]
94
+ feature_names = data.get("feature_names") or feature_names
95
+ elif y_data is None or x_data is None:
96
+ raise ValueError("必须提供文件路径(file_path)或直接数据(y_data和x_data)")
97
+
98
+ # 数据验证和转换
99
+ x_data = DataValidator.convert_to_2d_list(x_data)
100
+ DataValidator.validate_ols_gmm_data(y_data, x_data, feature_names)
101
+
102
+ # 2. 调用核心算法(复用!)
103
+ result: CoreOLSResult = core_ols_regression(
104
+ y_data=y_data,
105
+ x_data=x_data,
106
+ feature_names=feature_names,
107
+ constant=constant,
108
+ confidence_level=confidence_level
109
+ )
110
+
111
+ # 3. 格式化输出
112
+ if output_format == "json":
113
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
114
+ if save_path:
115
+ OutputFormatter.save_to_file(json_result, save_path)
116
+ return f"分析完成!结果已保存到: {save_path}\n\n{json_result}"
117
+ return json_result
118
+ else:
119
+ # 尝试使用格式化器,失败则回退到JSON
120
+ try:
121
+ formatted = OutputFormatter.format_ols_result(result, output_format)
122
+ if save_path:
123
+ OutputFormatter.save_to_file(formatted, save_path)
124
+ return f"分析完成!\n\n{formatted}\n\n已保存到: {save_path}"
125
+ return formatted
126
+ except Exception as e:
127
+ # 回退到JSON格式
128
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
129
+ warning = f"警告: {output_format}格式化失败({str(e)}),返回JSON格式\n\n"
130
+ if save_path:
131
+ OutputFormatter.save_to_file(json_result, save_path)
132
+ return f"{warning}分析完成!结果已保存到: {save_path}\n\n{json_result}"
133
+ return warning + json_result
134
+
135
+ @staticmethod
136
+ def mle_estimation(
137
+ data: Optional[List[float]] = None,
138
+ file_path: Optional[str] = None,
139
+ distribution: str = "normal",
140
+ initial_params: Optional[List[float]] = None,
141
+ confidence_level: float = 0.95,
142
+ output_format: str = "json",
143
+ save_path: Optional[str] = None
144
+ ) -> str:
145
+ """
146
+ MLE估计适配器
147
+
148
+ 优势:复用econometrics/核心算法
149
+ """
150
+ # 1. 数据准备
151
+ if file_path:
152
+ data_dict = MLEDataLoader.load_from_file(file_path)
153
+ data = data_dict["data"]
154
+ elif data is None:
155
+ raise ValueError("必须提供文件路径(file_path)或直接数据(data)")
156
+
157
+ # 2. 调用核心算法(复用!)
158
+ result: CoreMLEResult = core_mle_estimation(
159
+ data=data,
160
+ distribution=distribution,
161
+ initial_params=initial_params,
162
+ confidence_level=confidence_level
163
+ )
164
+
165
+ # 3. 格式化输出
166
+ if output_format == "json":
167
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
168
+ if save_path:
169
+ OutputFormatter.save_to_file(json_result, save_path)
170
+ return f"分析完成!结果已保存到: {save_path}\n\n{json_result}"
171
+ return json_result
172
+ else:
173
+ # 尝试使用格式化器,失败则回退到JSON
174
+ try:
175
+ formatted = OutputFormatter.format_mle_result(result, output_format)
176
+ if save_path:
177
+ OutputFormatter.save_to_file(formatted, save_path)
178
+ return f"分析完成!\n\n{formatted}\n\n已保存到: {save_path}"
179
+ return formatted
180
+ except Exception as e:
181
+ # 回退到JSON格式
182
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
183
+ warning = f"警告: {output_format}格式化失败({str(e)}),返回JSON格式\n\n"
184
+ if save_path:
185
+ OutputFormatter.save_to_file(json_result, save_path)
186
+ return f"{warning}分析完成!结果已保存到: {save_path}\n\n{json_result}"
187
+ return warning + json_result
188
+
189
+ @staticmethod
190
+ def gmm_estimation(
191
+ y_data: Optional[List[float]] = None,
192
+ x_data: Optional[List[List[float]]] = None,
193
+ file_path: Optional[str] = None,
194
+ instruments: Optional[List[List[float]]] = None,
195
+ feature_names: Optional[List[str]] = None,
196
+ constant: bool = True,
197
+ confidence_level: float = 0.95,
198
+ output_format: str = "json",
199
+ save_path: Optional[str] = None
200
+ ) -> str:
201
+ """
202
+ GMM估计适配器
203
+
204
+ 优势:复用econometrics/核心算法
205
+ 增强:添加数值稳定性检查
206
+ """
207
+ # 1. 数据准备
208
+ if file_path:
209
+ data = DataLoader.load_from_file(file_path)
210
+ y_data = data["y_data"]
211
+ x_data = data["x_data"]
212
+ feature_names = data.get("feature_names") or feature_names
213
+ elif y_data is None or x_data is None:
214
+ raise ValueError("必须提供文件路径(file_path)或直接数据(y_data和x_data)")
215
+
216
+ # 数据验证和转换
217
+ x_data = DataValidator.convert_to_2d_list(x_data)
218
+ DataValidator.validate_ols_gmm_data(y_data, x_data, feature_names)
219
+
220
+ # 转换工具变量格式
221
+ if instruments:
222
+ instruments = DataValidator.convert_to_2d_list(instruments)
223
+
224
+ # 2. 调用核心算法(复用!)
225
+ try:
226
+ result: CoreGMMResult = core_gmm_estimation(
227
+ y_data=y_data,
228
+ x_data=x_data,
229
+ instruments=instruments,
230
+ feature_names=feature_names,
231
+ constant=constant,
232
+ confidence_level=confidence_level
233
+ )
234
+ except Exception as e:
235
+ # 提供更详细的错误信息
236
+ error_msg = f"GMM估计失败: {str(e)}\n"
237
+ error_msg += "可能原因:\n"
238
+ error_msg += "1. 数据存在多重共线性\n"
239
+ error_msg += "2. 工具变量不足或无效\n"
240
+ error_msg += "3. 矩阵奇异(数值不稳定)\n"
241
+ error_msg += "建议:\n"
242
+ error_msg += "- 检查数据质量\n"
243
+ error_msg += "- 增加工具变量数量\n"
244
+ error_msg += "- 尝试标准化数据\n"
245
+ raise ValueError(error_msg) from e
246
+
247
+ # 3. 格式化输出
248
+ if output_format == "json":
249
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
250
+ if save_path:
251
+ OutputFormatter.save_to_file(json_result, save_path)
252
+ return f"分析完成!结果已保存到: {save_path}\n\n{json_result}"
253
+ return json_result
254
+ else:
255
+ # 尝试使用格式化器,失败则回退到JSON
256
+ try:
257
+ formatted = OutputFormatter.format_gmm_result(result, output_format)
258
+ if save_path:
259
+ OutputFormatter.save_to_file(formatted, save_path)
260
+ return f"分析完成!\n\n{formatted}\n\n已保存到: {save_path}"
261
+ return formatted
262
+ except Exception as e:
263
+ # 回退到JSON格式
264
+ json_result = json.dumps(result.dict(), ensure_ascii=False, indent=2)
265
+ warning = f"警告: {output_format}格式化失败({str(e)}),返回JSON格式\n\n"
266
+ if save_path:
267
+ OutputFormatter.save_to_file(json_result, save_path)
268
+ return f"{warning}分析完成!结果已保存到: {save_path}\n\n{json_result}"
269
+ return warning + json_result
270
+
271
+
272
+ # 便捷别名
273
+ ols_adapter = EconometricsAdapter.ols_regression
274
+ mle_adapter = EconometricsAdapter.mle_estimation
275
+
276
+ # 导入模型规范、诊断和稳健推断适配器
277
+ from .model_specification_adapter import (
278
+ diagnostic_tests_adapter,
279
+ gls_adapter,
280
+ wls_adapter,
281
+ robust_errors_adapter,
282
+ model_selection_adapter,
283
+ regularization_adapter,
284
+ simultaneous_equations_adapter
285
+ )
286
+ gmm_adapter = EconometricsAdapter.gmm_estimation