日志展示优化

This commit is contained in:
ddrwode
2026-02-11 14:57:34 +08:00
parent 53d27662e2
commit c3817c7937
3 changed files with 289 additions and 20 deletions

6
1111
View File

@@ -24,14 +24,18 @@ Abc12345678
bitmart\框架.py 读取这个代码文件夹
基础开仓逻辑
基于前一根有效 K 线(实体 ≥ 0.1
基于前一根有效 K 线(实体涨幅 ≥ 0.1
做多触发价 = 当前 k 线开盘价 + 上一根实体 / 3
做空触发价 = 当前 k 线开盘价 - 上一根实体 / 3
反手信号:
基于前一根有效 K 线(实体涨幅 ≥ 0.1
持空反手做多:价格涨到 当前k线开仓价 + 前一根实体 / 3
持多反手做空:价格跌到 当前k线开仓价 - 前一根实体 / 3
基本开场和反手信号都是基于实体涨幅大于 0.1% 的 k 线,如果没有就再看上一根,如果上一根也没有,就再往上找,直到找到为止
止盈:
如果当前开多,当前这根 5 分钟k 线开盘价到最高价涨幅大于 0.4%,然后就将这根 k 线分成 4等份回调到四分之三时止盈平仓回调到四分之 二时,开同向仓位
如果当前开空,当前这根 5 分钟k 线开盘价到最低价跌幅大于 0.4%,然后就将这根 k 线分成 4等份反弹到四分之三时止盈平仓反弹到四分之 二时,开同向仓位

View File

@@ -273,25 +273,55 @@ class BitmartFuturesTransaction:
logger.info(f"[止盈日志] 时间={time_str} | 操作={operation} | 原因={reason}")
def _write_open_log(self, operation: str, reason: str, current_kline: dict, prev_kline: dict | None):
"""写入策略开仓日志文件时间、参考的两根K线、操作、开仓原因"""
"""写入策略开仓日志文件时间、参考的两根K线、操作、开仓原因、计算参数"""
try:
date_str = datetime.now().strftime("%Y%m%d")
log_file = self.strategy_log_dir / f"strategy_log_{date_str}.txt"
time_str = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
# 当前K线信息
cur = current_kline
cur_line = f"id={cur['id']} open={cur['open']:.2f} high={cur['high']:.2f} low={cur['low']:.2f} close={cur['close']:.2f}"
# 上一根K线信息和计算参数
if prev_kline:
prev = prev_kline
prev_line = f"id={prev['id']} open={prev['open']:.2f} high={prev['high']:.2f} low={prev['low']:.2f} close={prev['close']:.2f}"
prev_entity = abs(prev['close'] - prev['open'])
prev_entity_pct = (prev_entity / prev['open']) * 100 if prev['open'] else 0
prev_line = (
f"id={prev['id']} open={prev['open']:.2f} high={prev['high']:.2f} "
f"low={prev['low']:.2f} close={prev['close']:.2f}\n"
f" 实体大小={prev_entity:.4f} ({prev_entity_pct:.3f}%) "
f"实体/3={prev_entity/3:.4f}"
)
# 计算触发价
base_open = cur['open']
long_trigger = base_open + prev_entity / 3
short_trigger = base_open - prev_entity / 3
calc_params = (
f"\n计算参数:\n"
f" ├─ 实体涨幅阈值: {self.min_prev_entity_pct}%\n"
f" ├─ 当前K线开盘价: {base_open:.2f}\n"
f" ├─ 上一根实体大小: {prev_entity:.4f}\n"
f" ├─ 上一根实体/3: {prev_entity/3:.4f}\n"
f" ├─ 做多触发价: {base_open:.2f} + {prev_entity/3:.4f} = {long_trigger:.2f}\n"
f" └─ 做空触发价: {base_open:.2f} - {prev_entity/3:.4f} = {short_trigger:.2f}"
)
else:
prev_line = "(无)"
calc_params = ""
block = (
f"\n{'='*60}\n"
f"\n{'='*80}\n"
f"时间: {time_str}\n"
f"操作: {operation}\n"
f"参考K线:\n 当前K线: {cur_line}\n 上一根K线: {prev_line}\n"
f"参考K线:\n"
f" 当前K线: {cur_line}\n"
f" 上一根K线: {prev_line}"
f"{calc_params}\n"
f"开仓原因: {reason}\n"
f"{'='*60}\n"
f"{'='*80}\n"
)
with open(log_file, "a", encoding="utf-8") as f:
f.write(block)
@@ -419,35 +449,54 @@ class BitmartFuturesTransaction:
"""
# 计算上一根K线实体主循环已保证所选 prev 实体涨幅 >= min_prev_entity_pct
prev_entity = self.calculate_entity(prev_kline)
prev_entity_pct = (prev_entity / prev_kline['open']) * 100 if prev_kline['open'] else 0
# 计算触发价当前K线开盘价 ± 上一根实体/3
base_open = current_kline['open']
long_trigger = base_open + prev_entity / 3
short_trigger = base_open - prev_entity / 3
logger.info(f"当前价格: {current_price:.2f}, 上一根实体: {prev_entity:.4f}")
logger.info(f"当前K线开盘价: {base_open:.2f}")
logger.info(f"做多触发价: {long_trigger:.2f}, 做空触发价: {short_trigger:.2f}")
# 详细日志:显示计算依据
logger.info("=" * 80)
logger.info(f"【信号检测】当前价格: {current_price:.2f}")
logger.info(f"【参考K线】上一根K线 ID: {prev_kline['id']}")
logger.info(f" ├─ 开盘价: {prev_kline['open']:.2f}")
logger.info(f" ├─ 收盘价: {prev_kline['close']:.2f}")
logger.info(f" ├─ 实体大小: {prev_entity:.4f} ({prev_entity_pct:.3f}%)")
logger.info(f" └─ 实体/3: {prev_entity/3:.4f}")
logger.info(f"【当前K线】ID: {current_kline['id']}, 开盘价: {base_open:.2f}")
logger.info(f"【触发价格】")
logger.info(f" ├─ 做多触发价 = {base_open:.2f} + {prev_entity/3:.4f} = {long_trigger:.2f}")
logger.info(f" └─ 做空触发价 = {base_open:.2f} - {prev_entity/3:.4f} = {short_trigger:.2f}")
logger.info("=" * 80)
# 无持仓时检查开仓信号
if self.start == 0:
if current_price >= long_trigger:
logger.info(f"触发做多信号!价格 {current_price:.2f} >= 触发价 {long_trigger:.2f}")
logger.success(f"触发做多信号!")
logger.success(f" 当前价格 {current_price:.2f} >= 做多触发价 {long_trigger:.2f}")
logger.success(f" 超出触发价: {current_price - long_trigger:.4f} ({(current_price - long_trigger)/long_trigger*100:.3f}%)")
return ('long', long_trigger)
elif current_price <= short_trigger:
logger.info(f"触发做空信号!价格 {current_price:.2f} <= 触发价 {short_trigger:.2f}")
logger.success(f"触发做空信号!")
logger.success(f" 当前价格 {current_price:.2f} <= 做空触发价 {short_trigger:.2f}")
logger.success(f" 低于触发价: {short_trigger - current_price:.4f} ({(short_trigger - current_price)/short_trigger*100:.3f}%)")
return ('short', short_trigger)
# 持多仓时检查反手信号
elif self.start == 1:
if current_price <= short_trigger:
logger.info(f"持多反手做空!价格 {current_price:.2f} <= 触发价 {short_trigger:.2f}")
logger.warning(f"⚠️ 持多反手做空信号")
logger.warning(f" 当前价格 {current_price:.2f} <= 做空触发价 {short_trigger:.2f}")
logger.warning(f" 低于触发价: {short_trigger - current_price:.4f} ({(short_trigger - current_price)/short_trigger*100:.3f}%)")
return ('reverse_short', short_trigger)
# 持空仓时检查反手信号
elif self.start == -1:
if current_price >= long_trigger:
logger.info(f"持空反手做多!价格 {current_price:.2f} >= 触发价 {long_trigger:.2f}")
logger.warning(f"⚠️ 持空反手做多信号")
logger.warning(f" 当前价格 {current_price:.2f} >= 做多触发价 {long_trigger:.2f}")
logger.warning(f" 超出触发价: {current_price - long_trigger:.4f} ({(current_price - long_trigger)/long_trigger*100:.3f}%)")
return ('reverse_long', long_trigger)
return None
@@ -671,15 +720,21 @@ class BitmartFuturesTransaction:
current_kline = formatted[-1]
prev_kline = None
# 向前搜索符合条件的K线实体涨幅 >= 阈值)
logger.debug(f"开始搜索上一根有效K线实体涨幅阈值: {self.min_prev_entity_pct}%")
for i in range(len(formatted) - 2, -1, -1):
k = formatted[i]
entity = abs(k['close'] - k['open'])
entity_pct = entity / k['open'] * 100 if k['open'] else 0
logger.debug(f" 检查K线 id={k['id']}: 实体涨幅={entity_pct:.3f}%")
if entity_pct >= self.min_prev_entity_pct:
prev_kline = k
logger.info(f"✓ 找到上一根有效K线: id={k['id']}, 实体涨幅={entity_pct:.3f}%")
break
if prev_kline is None:
logger.info(f"没有实体涨幅>={self.min_prev_entity_pct:.3f}%的上一根K线跳过信号检测")
logger.warning(f"没有实体涨幅>={self.min_prev_entity_pct:.3f}%的上一根K线跳过信号检测")
time.sleep(0.1)
continue
@@ -850,19 +905,44 @@ class BitmartFuturesTransaction:
self.reverse_count_kline_id = current_kline_time
self.reverse_count_in_kline = 0
self.reverse_count_in_kline += 1
# 写入开仓日志参考的两根K线 + 开仓原因
# 写入开仓日志参考的两根K线 + 开仓原因 + 详细计算参数
sig_type, trigger_price = signal
op_name = {"long": "开多", "short": "开空", "reverse_long": "反手做多", "reverse_short": "反手做空"}.get(sig_type, sig_type)
# 计算详细参数
prev_entity = abs(prev_kline['close'] - prev_kline['open'])
prev_entity_pct = (prev_entity / prev_kline['open']) * 100 if prev_kline['open'] else 0
base_open = current_kline['open']
price_diff = abs(current_price - trigger_price)
price_diff_pct = (price_diff / trigger_price) * 100 if trigger_price else 0
if sig_type == "long":
open_reason = f"三分之一策略:当前价{current_price:.2f}>=开仓做多价{trigger_price:.2f}(当前开盘+上一根实体1/3)"
open_reason = (
f"三分之一策略开多:当前价{current_price:.2f} >= 触发价{trigger_price:.2f}\n"
f" 计算: 触发价 = 当前开盘{base_open:.2f} + 实体/3({prev_entity/3:.4f}) = {trigger_price:.2f}\n"
f" 超出触发价: {price_diff:.4f} ({price_diff_pct:.3f}%)"
)
elif sig_type == "short":
open_reason = f"三分之一策略:当前价{current_price:.2f}<=开仓做空价{trigger_price:.2f}(当前开盘-上一根实体1/3)"
open_reason = (
f"三分之一策略开空:当前价{current_price:.2f} <= 触发价{trigger_price:.2f}\n"
f" 计算: 触发价 = 当前开盘{base_open:.2f} - 实体/3({prev_entity/3:.4f}) = {trigger_price:.2f}\n"
f" 低于触发价: {price_diff:.4f} ({price_diff_pct:.3f}%)"
)
elif sig_type == "reverse_long":
open_reason = f"持空反手做多:当前价{current_price:.2f}>=做多触发价{trigger_price:.2f}(当前开盘+上一根实体1/3)"
open_reason = (
f"持空反手做多:当前价{current_price:.2f} >= 触发价{trigger_price:.2f}\n"
f" 计算: 触发价 = 当前开盘{base_open:.2f} + 实体/3({prev_entity/3:.4f}) = {trigger_price:.2f}\n"
f" 超出触发价: {price_diff:.4f} ({price_diff_pct:.3f}%)"
)
else:
open_reason = f"持多反手做空:当前价{current_price:.2f}<=做空触发价{trigger_price:.2f}(当前开盘-上一根实体1/3)"
open_reason = (
f"持多反手做空:当前价{current_price:.2f} <= 触发价{trigger_price:.2f}\n"
f" 计算: 触发价 = 当前开盘{base_open:.2f} - 实体/3({prev_entity/3:.4f}) = {trigger_price:.2f}\n"
f" 低于触发价: {price_diff:.4f} ({price_diff_pct:.3f}%)"
)
self._write_open_log(op_name, open_reason, current_kline, prev_kline)
logger.success(f"交易执行完成: {signal[0]}, 当前持仓状态: {self.start}")
logger.success(f"🎉 交易执行完成: {op_name}, 当前持仓状态: {self.start}")
page_start = True
else:
logger.warning(f"交易执行失败或被阻止: {signal[0]}")

185
bitmart/日志说明.md Normal file
View File

@@ -0,0 +1,185 @@
# 交易日志说明文档
## 📋 日志优化内容
已优化开仓操作的日志输出,现在包含详细的计算依据和参数信息。
---
## 🔍 实时控制台日志示例
### 1. K线搜索日志
```
开始搜索上一根有效K线实体涨幅阈值: 0.1%
检查K线 id=1707825600: 实体涨幅=0.085%
检查K线 id=1707825300: 实体涨幅=0.156%
✓ 找到上一根有效K线: id=1707825300, 实体涨幅=0.156%
```
### 2. 信号检测详细日志
```
================================================================================
【信号检测】当前价格: 3245.67
【参考K线】上一根K线 ID: 1707825300
├─ 开盘价: 3240.00
├─ 收盘价: 3245.05
├─ 实体大小: 5.0500 (0.156%)
└─ 实体/3: 1.6833
【当前K线】ID: 1707825900, 开盘价: 3244.50
【触发价格】
├─ 做多触发价 = 3244.50 + 1.6833 = 3246.18
└─ 做空触发价 = 3244.50 - 1.6833 = 3242.82
================================================================================
```
### 3. 触发信号日志
#### 开多信号
```
✅ 触发做多信号!
当前价格 3247.50 >= 做多触发价 3246.18
超出触发价: 1.3200 (0.041%)
```
#### 开空信号
```
✅ 触发做空信号!
当前价格 3242.00 <= 做空触发价 3242.82
低于触发价: 0.8200 (0.025%)
```
#### 反手信号
```
⚠️ 持多反手做空信号!
当前价格 3241.50 <= 做空触发价 3242.82
低于触发价: 1.3200 (0.041%)
```
---
## 📝 策略日志文件示例
日志文件位置: `bitmart/strategy_log_YYYYMMDD.txt`
### 开多日志示例
```
================================================================================
时间: 2024-02-13 14:35:22
操作: 开多
参考K线:
当前K线: id=1707825900 open=3244.50 high=3248.20 low=3243.10 close=3246.80
上一根K线: id=1707825300 open=3240.00 high=3245.50 low=3239.20 close=3245.05
实体大小=5.0500 (0.156%) 实体/3=1.6833
计算参数:
├─ 实体涨幅阈值: 0.1%
├─ 当前K线开盘价: 3244.50
├─ 上一根实体大小: 5.0500
├─ 上一根实体/3: 1.6833
├─ 做多触发价: 3244.50 + 1.6833 = 3246.18
└─ 做空触发价: 3244.50 - 1.6833 = 3242.82
开仓原因: 三分之一策略开多当前价3247.50 >= 触发价3246.18
计算: 触发价 = 当前开盘3244.50 + 实体/3(1.6833) = 3246.18
超出触发价: 1.3200 (0.041%)
================================================================================
```
### 反手做空日志示例
```
================================================================================
时间: 2024-02-13 14:38:45
操作: 反手做空
参考K线:
当前K线: id=1707826200 open=3248.00 high=3250.30 low=3241.50 close=3242.10
上一根K线: id=1707825600 open=3246.00 high=3250.80 low=3245.20 close=3250.50
实体大小=4.5000 (0.139%) 实体/3=1.5000
计算参数:
├─ 实体涨幅阈值: 0.1%
├─ 当前K线开盘价: 3248.00
├─ 上一根实体大小: 4.5000
├─ 上一根实体/3: 1.5000
├─ 做多触发价: 3248.00 + 1.5000 = 3249.50
└─ 做空触发价: 3248.00 - 1.5000 = 3246.50
开仓原因: 持多反手做空当前价3245.80 <= 触发价3246.50
计算: 触发价 = 当前开盘3248.00 - 实体/3(1.5000) = 3246.50
低于触发价: 0.7000 (0.021%)
================================================================================
```
---
## 📊 日志包含的关键信息
### 1. K线选择信息
- ✅ 搜索过程显示每根K线的实体涨幅
- ✅ 选中的K线ID和实体涨幅百分比
- ✅ 实体涨幅阈值默认0.1%
### 2. 计算参数
- ✅ 当前K线开盘价
- ✅ 上一根K线的开盘价、收盘价、最高价、最低价
- ✅ 上一根K线实体大小绝对值和百分比
- ✅ 实体/3的具体数值
### 3. 触发价格
- ✅ 做多触发价的完整计算公式
- ✅ 做空触发价的完整计算公式
- ✅ 当前价格与触发价的差值(绝对值和百分比)
### 4. 开仓原因
- ✅ 策略类型(开多/开空/反手做多/反手做空)
- ✅ 当前价格
- ✅ 触发价格
- ✅ 价格差异(超出或低于触发价的幅度)
---
## 🎯 日志级别说明
| 级别 | 用途 | 示例 |
|------|------|------|
| `DEBUG` | K线搜索过程 | 检查每根K线的实体涨幅 |
| `INFO` | 一般信息 | 找到有效K线、信号检测参数 |
| `SUCCESS` | 成功操作 | 触发信号、交易执行成功 |
| `WARNING` | 警告信息 | 反手信号、未找到有效K线 |
| `ERROR` | 错误信息 | 交易失败、验证失败 |
---
## 💡 使用建议
1. **实时监控**: 关注控制台输出的信号检测日志,了解当前市场状态
2. **策略分析**: 查看日志文件中的详细计算参数,分析开仓时机
3. **参数优化**: 根据日志中的实体涨幅数据,调整 `min_prev_entity_pct` 阈值
4. **回测验证**: 使用日志文件中的完整信息进行策略回测和优化
---
## 🔧 可调整参数
在代码第70行可以调整实体涨幅阈值
```python
self.min_prev_entity_pct = 0.1 # 上一根K线实体涨幅%
```
建议范围: 0.05% - 0.3%
- 较小值更容易找到参考K线但可能包含噪音
- 较大值参考K线更有效但可能长时间找不到
---
## 📈 日志优化效果
| 优化项 | 优化前 | 优化后 |
|--------|--------|--------|
| 计算依据 | ❌ 无 | ✅ 完整显示 |
| 参数信息 | ❌ 无 | ✅ 详细列出 |
| K线选择过程 | ❌ 无 | ✅ 实时显示 |
| 价格差异 | ❌ 无 | ✅ 绝对值+百分比 |
| 日志可读性 | ⭐⭐⭐ | ⭐⭐⭐⭐⭐ |
现在您可以清楚地看到每次开仓的完整计算过程和依据!🎉