openfund-core 1.0.8__tar.gz → 1.0.9__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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: openfund-core
3
- Version: 1.0.8
3
+ Version: 1.0.9
4
4
  Summary: Openfund-core.
5
5
  Requires-Python: >=3.9,<4.0
6
6
  Classifier: Programming Language :: Python :: 3
@@ -1,6 +1,6 @@
1
1
  [tool.poetry]
2
2
  name = "openfund-core"
3
- version = "1.0.8"
3
+ version = "1.0.9"
4
4
  description = "Openfund-core."
5
5
  authors = []
6
6
  readme = "README.md"
@@ -1,4 +1,5 @@
1
1
  import logging
2
+ from decimal import Decimal
2
3
  from core.smc.SMCStruct import SMCStruct
3
4
 
4
5
 
@@ -27,20 +28,17 @@ class SMCLiquidity(SMCStruct):
27
28
  df = data.copy()
28
29
 
29
30
  # 识别高点
30
- df[self.LIQU_HIGH_COL] = 0
31
+ df[self.LIQU_HIGH_COL] = Decimal(0.0)
31
32
  for i in range(pivot_length, len(df) - pivot_length):
32
33
  if df[self.HIGH_COL].iloc[i] == max(df[self.HIGH_COL].iloc[i-pivot_length:i+pivot_length+1]):
33
- df.loc[df.index[i], self.LIQU_HIGH_COL] = df[self.HIGH_COL].iloc[i]
34
-
34
+ df.loc[df.index[i], self.LIQU_HIGH_COL] = df[self.HIGH_COL].iloc[i]
35
35
  # 识别低点
36
- df[self.LIQU_LOW_COL] = 0
36
+ df[self.LIQU_LOW_COL] = Decimal(0.0)
37
37
  for i in range(pivot_length, len(df) - pivot_length):
38
38
 
39
39
  if df[self.LOW_COL].iloc[i] == min(df[self.LOW_COL].iloc[i-pivot_length:i+pivot_length+1]):
40
40
  df.loc[df.index[i], self.LIQU_LOW_COL] = df[self.LOW_COL].iloc[i]
41
41
 
42
-
43
-
44
42
  return df
45
43
 
46
44
  def find_EQH_EQL(self, data, trend, end_idx=-1, atr_offset=0.1) -> dict:
@@ -63,7 +61,7 @@ class SMCLiquidity(SMCStruct):
63
61
  try:
64
62
  self.check_columns(df, check_columns)
65
63
  except ValueError as e:
66
- self.logger.warning(f"DataFrame must contain columns {check_columns} : {str(e)}")
64
+ # self.logger.warning(f"DataFrame must contain columns {check_columns} : {str(e)}")
67
65
  df = self._identify_liquidity_pivots(df)
68
66
 
69
67
  df = df[(df[self.LIQU_HIGH_COL] > 0) | (df[self.LIQU_LOW_COL] > 0)]
@@ -9,13 +9,14 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
9
9
  PD_LOW_COL = "pd_low"
10
10
  PD_MID_COL = "pd_mid"
11
11
  PD_TYPE_COL = "pd_type"
12
+ PD_WAS_BALANCED_COL = "pd_was_balanced"
12
13
 
13
14
  def __init__(self):
14
15
  super().__init__()
15
16
  self.logger = logging.getLogger(__name__)
16
17
 
17
18
  def find_PDArrays(
18
- self, struct: pd.DataFrame, side, start_index=-1, check_balanced=True,
19
+ self, struct: pd.DataFrame, side, start_index=-1, balanced=False,
19
20
  ) -> pd.DataFrame:
20
21
  """_summary_
21
22
  寻找PDArrays,包括Fair Value Gap (FVG)|Order Block (OB)|Breaker Block(BB)|Mitigation Block(BB)
@@ -23,7 +24,7 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
23
24
  data (pd.DataFrame): K线数据
24
25
  side (_type_): 交易方向 'buy'|'sell'
25
26
  start_index (int): 开始查找索引的起点,默认为-1
26
- check_balanced (bool): PD是否有效,默认为True。PD被crossed过,则是无效PD
27
+ balanced (bool): PD是否有效,默认为False。PD被crossed过,则是无效PD
27
28
 
28
29
  Returns:
29
30
  pd.DataFrame: _description_
@@ -36,11 +37,14 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
36
37
  else struct.copy().iloc[max(0, start_index - 1) :]
37
38
  )
38
39
 
39
- df_FVGs = self.find_FVGs(df, side, check_balanced, start_index)
40
- # self.logger.info(f"fvgs:\n{df_FVGs[['timestamp', self.FVG_SIDE, self.FVG_TOP, self.FVG_BOT, self.FVG_WAS_BALANCED]]}")
40
+ df_FVGs = self.find_FVGs(df, side, start_index)
41
41
 
42
+ if not balanced:
43
+ df_FVGs = df_FVGs[~df_FVGs[self.FVG_WAS_BALANCED]]
44
+ # self.logger.info(f"fvgs:\n{df_FVGs[['timestamp', self.FVG_SIDE, self.FVG_TOP, self.FVG_BOT, self.FVG_WAS_BALANCED]]}")
42
45
 
43
- df_OBs = self.find_OBs(df, side, start_index, is_valid=check_balanced)
46
+ is_valid = not balanced
47
+ df_OBs = self.find_OBs(struct=df, side=side, start_index=start_index, is_valid=is_valid)
44
48
  # self.logger.info("find_OBs:\n %s", df_OBs)
45
49
 
46
50
  # 使用更简洁的方式重命名和合并时间戳列
@@ -59,6 +63,10 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
59
63
  df_PDArrays[self.TIMESTAMP_COL] = df_PDArrays[timestamp_mapping[self.TIMESTAMP_COL][0]].fillna(
60
64
  df_PDArrays[timestamp_mapping[self.TIMESTAMP_COL][1]]
61
65
  )
66
+
67
+ df_PDArrays[self.PD_WAS_BALANCED_COL] = df_PDArrays[[self.OB_WAS_CROSSED, self.FVG_WAS_BALANCED]].apply(
68
+ lambda x: x.iloc[0] if pd.notna(x.iloc[0]) else x.iloc[1], axis=1)
69
+
62
70
  df_PDArrays[self.PD_TYPE_COL] = df_PDArrays[[self.FVG_SIDE, self.OB_DIRECTION_COL]].apply(
63
71
  lambda x: 'FVG-OB' if pd.notna(x.iloc[0]) and pd.notna(x.iloc[1]) else 'FVG' if pd.notna(x.iloc[0]) else 'OB', axis=1
64
72
  )
@@ -68,10 +76,12 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
68
76
  df_PDArrays.loc[:, self.PD_MID_COL] = (df_PDArrays[self.PD_HIGH_COL] + df_PDArrays[self.PD_LOW_COL]) / 2
69
77
 
70
78
 
71
- return df_PDArrays
79
+ # 根据balanced参数过滤PDArrays,返回符合条件的数据
80
+
81
+ return df_PDArrays[df_PDArrays[self.PD_WAS_BALANCED_COL] == balanced]
72
82
 
73
83
 
74
- def get_latest_PDArray(self, df_PDArrays: pd.DataFrame, side, start_index=-1, check_balanced=True, mask:str=None) -> dict:
84
+ def get_latest_PDArray(self, df_PDArrays: pd.DataFrame, side, start_index=-1, balanced=False, mask=None) -> dict:
75
85
  """_summary_
76
86
  过滤PDArrays,只保留指定方向的PDArrays
77
87
  Args:
@@ -89,16 +99,22 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
89
99
  self.check_columns(df, check_columns)
90
100
  except ValueError as e:
91
101
  df = self.build_struct(df)
92
-
93
- df = self.find_PDArrays(df, side, start_index, check_balanced)
94
102
 
95
- if mask:
96
- df = df[df[mask]]
103
+
104
+ check_columns = [self.PD_TYPE_COL]
105
+ try:
106
+ self.check_columns(df, check_columns)
107
+ except ValueError as e:
108
+ df = self.find_PDArrays(df, side, start_index, balanced)
109
+
110
+ if mask is not None:
111
+ df = df[mask]
97
112
 
98
113
  if len(df) == 0:
99
114
  self.logger.info("未找到PDArray.")
100
115
  return None
101
116
  else:
117
+ self.logger.debug(f"PDArray:\n{df[[self.TIMESTAMP_COL, self.PD_TYPE_COL, self.PD_HIGH_COL, self.PD_LOW_COL, self.PD_MID_COL,self.PD_WAS_BALANCED_COL,self.OB_WAS_CROSSED,self.FVG_WAS_BALANCED]]}")
102
118
  last_pd = df.iloc[-1]
103
119
  return {
104
120
  self.TIMESTAMP_COL: last_pd[self.TIMESTAMP_COL],
@@ -106,4 +122,5 @@ class SMCPDArray(SMCFVG,SMCOrderBlock):
106
122
  self.PD_HIGH_COL: last_pd[self.PD_HIGH_COL],
107
123
  self.PD_LOW_COL: last_pd[self.PD_LOW_COL],
108
124
  self.PD_MID_COL: last_pd[self.PD_MID_COL],
125
+ self.PD_WAS_BALANCED_COL: last_pd[self.PD_WAS_BALANCED_COL],
109
126
  }
File without changes