gfrdegdergr
This commit is contained in:
139
bieget/main.py
Normal file
139
bieget/main.py
Normal file
@@ -0,0 +1,139 @@
|
||||
import requests
|
||||
import datetime
|
||||
|
||||
cookies = {
|
||||
'bitget_lang': 'zh-CN',
|
||||
'_dx_kvani5r': '24e0dceb12f85d9a1279183ca29c09f772f8c61124e4eca228d8dd909c9b24b0019c2b9a',
|
||||
'OptanonAlertBoxClosed': 'Wed%20Sep%2024%202025%2017:12:32%20GMT+0800%20(%E4%B8%AD%E5%9B%BD%E6%A0%87%E5%87%86%E6%97%B6%E9%97%B4)',
|
||||
'OptanonConsent': 'isMarketing=1&isStatistic=1',
|
||||
'_cfuvid': 'IHXjOVVjx5iewfwL1nrgeHsZ6whu9s4iYYYvNvJvOQM-1758867462928-0.0.1.1-604800000',
|
||||
'dy_token': '68d630093VQFDNL1nUkv46lfDdhjHGYpoz9dddX1',
|
||||
'g_state': '{"i_l":0}',
|
||||
'theme': 'white',
|
||||
'BITGET_LOCAL_COOKIE': '{%22bitget_lang%22:%22zh-CN%22%2C%22bitget_unit%22:%22CNY%22%2C%22bitget_showasset%22:true%2C%22bitget_theme%22:%22white%22%2C%22bitget_layout%22:%22right%22%2C%22bitget_valuationunit%22:0%2C%22bitget_valuationunit_new%22:1%2C%22bitget_valuationunitandfiat%22:1%2C%22bitgt_login%22:false%2C%22theme%22:%22black%22%2C%22brand_simulation_trade%22:false%2C%22bitget_currency%22:%22%22}',
|
||||
'bt_rtoken': 'upex:session:id:1d00ce6487e37f4d7230a5aafe3ffc82e799156a86e9778bacb2310c7cf39b98',
|
||||
'bt_uid': '619BB9EC4D4A3F9FC1AC092D38818A00',
|
||||
'bt_sessonid': '0bf4ef42-798c-4f8d-8fe5-c07364d3b6b5',
|
||||
'bt_newsessionid': 'eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiI4ZjJmNDBjYS0zNTkyLTRiNmItOTdiMy01OWQ5MTU5Y2E2YmQ0NzQ5ODIwMTAiLCJ1aWQiOiIxV00rVjRqcTJYSVRQemdJVWhUMnNRPT0iLCJzdWIiOiJsenoqKipvbSIsImlwIjoiM3dNK05yTkxjQXVQTG95dWZkWkI1QT09IiwiZGlkIjoiSjBZZjQ1NkV5RUxaSGhaa2tWYnNQZTVlSFVYYUNKZS9CM21wTHJ5SHJWMTEyUklzWlFLTTVIQmtTNHlUUmhuVyIsInN0cyI6MCwiaWF0IjoxNzU4ODY3NTgxLCJleHAiOjE3NTkyOTk1ODEsInB1c2hpZCI6ImRka1NMR1VDak9Sd1pFdU1rMFlaMWc9PSIsImlzcyI6InVwZXgifQ.Buwhs7UF7dOnOAso8l-RIyc_A47UdWSeVMiwIonOdiY',
|
||||
'USD': 'CNY',
|
||||
'__cf_bm': '3AMy5P3a.qp5uEqe9d_DonCDcL621CKULNKaUpfn2rE-1758868368-1.0.1.1-JzjFQidqwDxVV3gJH8ls0NeCGe.nsK.SFYP0hPXUcupuLTBpscmBYQRMfAjeOlnaZRBsQROFL2fETfXatDwQwDHU7aHOT4IMwECKB3sTIN4',
|
||||
}
|
||||
|
||||
headers = {
|
||||
'accept': 'application/json, text/plain, */*',
|
||||
'accept-language': 'zh,zh-CN;q=0.9,zh-HK;q=0.8,en;q=0.7',
|
||||
'baggage': 'sentry-environment=online,sentry-release=905e3a416e2b0ad3c98a82ab9b94dd87f1a5c1fd,sentry-public_key=8aeef93d782e4ef5ae75634bfee9b590,sentry-trace_id=e7afec8af26a4480893c8b58257af49b',
|
||||
'cache-control': 'no-cache',
|
||||
'custom-token': '765eb29bf89843258756f8851ed5a48f',
|
||||
'deviceid': '7c88d47fdc39e5c422eff197b10d3485',
|
||||
'dy-token': '68d630093VQFDNL1nUkv46lfDdhjHGYpoz9dddX1',
|
||||
'language': 'zh_CN',
|
||||
'locale': 'zh_CN',
|
||||
'pragma': 'no-cache',
|
||||
'priority': 'u=1, i',
|
||||
'referer': 'https://www.bitget.com/zh-CN/futures/usdt/ETHUSDT',
|
||||
'sec-ch-ua': '"Chromium";v="140", "Not=A?Brand";v="24", "Google Chrome";v="140"',
|
||||
'sec-ch-ua-mobile': '?0',
|
||||
'sec-ch-ua-platform': '"Windows"',
|
||||
'sec-fetch-dest': 'empty',
|
||||
'sec-fetch-mode': 'cors',
|
||||
'sec-fetch-site': 'same-origin',
|
||||
'sentry-trace': 'e7afec8af26a4480893c8b58257af49b-8aacec1747b38bd7-0',
|
||||
'terminalcode': 'cc98a9dd01af7e2d50d9b9858723b25e',
|
||||
'terminaltype': '1',
|
||||
'tm': '1758868503025',
|
||||
'uhti': 'w17588685039139806ab12716',
|
||||
'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/140.0.0.0 Safari/537.36',
|
||||
'website': 'mix',
|
||||
# 'cookie': 'bitget_lang=zh-CN; _dx_kvani5r=24e0dceb12f85d9a1279183ca29c09f772f8c61124e4eca228d8dd909c9b24b0019c2b9a; OptanonAlertBoxClosed=Wed%20Sep%2024%202025%2017:12:32%20GMT+0800%20(%E4%B8%AD%E5%9B%BD%E6%A0%87%E5%87%86%E6%97%B6%E9%97%B4); OptanonConsent=isMarketing=1&isStatistic=1; _cfuvid=IHXjOVVjx5iewfwL1nrgeHsZ6whu9s4iYYYvNvJvOQM-1758867462928-0.0.1.1-604800000; dy_token=68d630093VQFDNL1nUkv46lfDdhjHGYpoz9dddX1; g_state={"i_l":0}; theme=white; BITGET_LOCAL_COOKIE={%22bitget_lang%22:%22zh-CN%22%2C%22bitget_unit%22:%22CNY%22%2C%22bitget_showasset%22:true%2C%22bitget_theme%22:%22white%22%2C%22bitget_layout%22:%22right%22%2C%22bitget_valuationunit%22:0%2C%22bitget_valuationunit_new%22:1%2C%22bitget_valuationunitandfiat%22:1%2C%22bitgt_login%22:false%2C%22theme%22:%22black%22%2C%22brand_simulation_trade%22:false%2C%22bitget_currency%22:%22%22}; bt_rtoken=upex:session:id:1d00ce6487e37f4d7230a5aafe3ffc82e799156a86e9778bacb2310c7cf39b98; bt_uid=619BB9EC4D4A3F9FC1AC092D38818A00; bt_sessonid=0bf4ef42-798c-4f8d-8fe5-c07364d3b6b5; bt_newsessionid=eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiI4ZjJmNDBjYS0zNTkyLTRiNmItOTdiMy01OWQ5MTU5Y2E2YmQ0NzQ5ODIwMTAiLCJ1aWQiOiIxV00rVjRqcTJYSVRQemdJVWhUMnNRPT0iLCJzdWIiOiJsenoqKipvbSIsImlwIjoiM3dNK05yTkxjQXVQTG95dWZkWkI1QT09IiwiZGlkIjoiSjBZZjQ1NkV5RUxaSGhaa2tWYnNQZTVlSFVYYUNKZS9CM21wTHJ5SHJWMTEyUklzWlFLTTVIQmtTNHlUUmhuVyIsInN0cyI6MCwiaWF0IjoxNzU4ODY3NTgxLCJleHAiOjE3NTkyOTk1ODEsInB1c2hpZCI6ImRka1NMR1VDak9Sd1pFdU1rMFlaMWc9PSIsImlzcyI6InVwZXgifQ.Buwhs7UF7dOnOAso8l-RIyc_A47UdWSeVMiwIonOdiY; USD=CNY; __cf_bm=3AMy5P3a.qp5uEqe9d_DonCDcL621CKULNKaUpfn2rE-1758868368-1.0.1.1-JzjFQidqwDxVV3gJH8ls0NeCGe.nsK.SFYP0hPXUcupuLTBpscmBYQRMfAjeOlnaZRBsQROFL2fETfXatDwQwDHU7aHOT4IMwECKB3sTIN4',
|
||||
}
|
||||
if __name__ == '__main__':
|
||||
|
||||
params = {
|
||||
'symbolId': 'ETHUSDT_UMCBL',
|
||||
'kLineStep': '1m',
|
||||
'kLineType': '1',
|
||||
'endTime': '1758864600000',
|
||||
}
|
||||
|
||||
response = requests.get(
|
||||
'https://www.bitget.com/v1/kline/getMoreKlineDataV2',
|
||||
params=params, cookies=cookies, headers=headers
|
||||
)
|
||||
|
||||
raw_data = response.json()["data"]
|
||||
|
||||
print(raw_data)
|
||||
|
||||
# 转换成字典格式,方便后续处理
|
||||
data = []
|
||||
for i in raw_data:
|
||||
data.append({
|
||||
'id': int(i[0]) // 1000, # 秒级时间戳
|
||||
'open': float(i[1]),
|
||||
'high': float(i[2]),
|
||||
'low': float(i[3]),
|
||||
'close': float(i[4]),
|
||||
})
|
||||
|
||||
print(i)
|
||||
|
||||
print(data)
|
||||
|
||||
# 按时间排序
|
||||
sorted_data = sorted(data, key=lambda x: x['id'])
|
||||
|
||||
print(sorted_data)
|
||||
|
||||
signals = 0
|
||||
wins = 0
|
||||
lig_price = 0
|
||||
low_price = 0
|
||||
|
||||
for idx in range(1, len(sorted_data) - 2): # 至少留两根 K 线验证
|
||||
prev = sorted_data[idx - 1]
|
||||
curr = sorted_data[idx]
|
||||
future = sorted_data[idx + 2]
|
||||
|
||||
prev_open, prev_close = prev['open'], prev['close']
|
||||
curr_open, curr_close = curr['open'], curr['close']
|
||||
future_close = future['close']
|
||||
|
||||
# 当前为涨
|
||||
if curr_close > curr_open:
|
||||
# 前一笔涨 + 包裹
|
||||
if prev_close > prev_open and curr_open < prev_open and curr_close > prev_close:
|
||||
signals += 1
|
||||
lig_price += (future_close - curr_close)
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
# 前一笔跌 + 反包
|
||||
elif prev_close < prev_open and curr_open < prev_close and curr_close > prev_open:
|
||||
signals += 1
|
||||
lig_price += (future_close - curr_close)
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
# 当前为跌
|
||||
elif curr_close < curr_open:
|
||||
# 前一笔跌 + 包裹
|
||||
if prev_close < prev_open and curr_open > prev_open and curr_close < prev_close:
|
||||
signals += 1
|
||||
low_price += (curr_close - future_close)
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
# 前一笔涨 + 反包
|
||||
elif prev_close > prev_open and curr_open > prev_close and curr_close < prev_open:
|
||||
signals += 1
|
||||
low_price += (curr_close - future_close)
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
if signals > 0:
|
||||
win_rate = wins / signals * 100
|
||||
print(f"信号数={signals}, 胜率={win_rate:.2f}%")
|
||||
else:
|
||||
print("没有找到符合条件的形态")
|
||||
|
||||
print("上涨盈亏合计:", lig_price)
|
||||
print("下跌盈亏合计:", low_price)
|
||||
167
回测数据/test1.py
167
回测数据/test1.py
@@ -1,6 +1,6 @@
|
||||
import datetime
|
||||
import requests
|
||||
import plotly.graph_objects as go
|
||||
from loguru import logger
|
||||
|
||||
headers = {
|
||||
'accept': 'application/json, text/plain, */*',
|
||||
@@ -20,76 +20,119 @@ headers = {
|
||||
}
|
||||
|
||||
if __name__ == '__main__':
|
||||
time_ser = datetime.datetime(2025, 9, 25)
|
||||
start_of_day = time_ser.replace(hour=0, minute=0, second=0, microsecond=0)
|
||||
end_of_day = time_ser.replace(hour=23, minute=59, second=59, microsecond=0)
|
||||
|
||||
start_timestamp = start_of_day.timestamp()
|
||||
end_timestamp = end_of_day.timestamp()
|
||||
zh_project = 0
|
||||
all_trades = [] # 存放所有交易记录
|
||||
|
||||
params = {
|
||||
'symbol': 'ETH-USDT',
|
||||
'period': '1min',
|
||||
'start': int(start_timestamp),
|
||||
'end': int(end_timestamp),
|
||||
}
|
||||
for i in range(1, 29):
|
||||
|
||||
response = requests.get('https://capi.websea.com/webApi/market/getKline', params=params, headers=headers)
|
||||
data = response.json()['result']['data']
|
||||
sorted_data = sorted(data, key=lambda x: x['id'])
|
||||
# 请求数据
|
||||
time_ser = datetime.datetime(2025, 9, i)
|
||||
start_of_day = time_ser.replace(hour=0, minute=0, second=0, microsecond=0)
|
||||
end_of_day = time_ser.replace(hour=23, minute=59, second=59, microsecond=0)
|
||||
params = {
|
||||
'symbol': 'ETH-USDT',
|
||||
'period': '1min',
|
||||
'start': int(start_of_day.timestamp()),
|
||||
'end': int(end_of_day.timestamp()),
|
||||
}
|
||||
|
||||
# 处理成列表
|
||||
times = [datetime.datetime.fromtimestamp(d['id']) for d in sorted_data]
|
||||
opens = [float(d['open']) for d in sorted_data]
|
||||
highs = [float(d['high']) for d in sorted_data]
|
||||
lows = [float(d['low']) for d in sorted_data]
|
||||
closes = [float(d['close']) for d in sorted_data]
|
||||
response = requests.get('https://capi.websea.com/webApi/market/getKline', params=params, headers=headers)
|
||||
data = response.json()['result']['data']
|
||||
sorted_data = sorted(data, key=lambda x: x['id'])
|
||||
|
||||
# 找到策略点位
|
||||
signal_times = []
|
||||
signal_prices = []
|
||||
signals = 0
|
||||
wins = 0
|
||||
|
||||
for i in range(1, len(sorted_data)):
|
||||
current_data = sorted_data[i]
|
||||
prev_data = sorted_data[i - 1]
|
||||
lig_price = 0
|
||||
low_price = 0
|
||||
|
||||
if float(current_data['open']) < float(current_data['close']): # 当前上涨
|
||||
if float(prev_data['open']) < float(prev_data['close']): # 前一笔上涨
|
||||
if float(current_data['open']) < float(prev_data['open']) and float(current_data['close']) > float(prev_data['close']):
|
||||
signal_times.append(datetime.datetime.fromtimestamp(current_data['id']))
|
||||
signal_prices.append(float(current_data['close']))
|
||||
else: # 前一笔下跌
|
||||
if float(current_data['open']) < float(prev_data['close']) and float(current_data['close']) > float(prev_data['open']):
|
||||
signal_times.append(datetime.datetime.fromtimestamp(current_data['id']))
|
||||
signal_prices.append(float(current_data['close']))
|
||||
for idx in range(1, len(sorted_data) - 5): # 需要至少留两根K线做验证
|
||||
prev = sorted_data[idx - 1] # 前一笔
|
||||
curr = sorted_data[idx] # 当前这笔
|
||||
future = sorted_data[idx + 5] # 两根后的K线
|
||||
|
||||
# 绘制K线图
|
||||
fig = go.Figure(data=[
|
||||
go.Candlestick(
|
||||
x=times,
|
||||
open=opens,
|
||||
high=highs,
|
||||
low=lows,
|
||||
close=closes,
|
||||
name="K线"
|
||||
prev_open, prev_close = float(prev['open']), float(prev['close'])
|
||||
curr_open, curr_close = float(curr['open']), float(curr['close'])
|
||||
future_close = float(future['close'])
|
||||
|
||||
# 当前为涨
|
||||
if curr_close > curr_open:
|
||||
# 前一笔涨 + 包裹
|
||||
if prev_close > prev_open and curr_open < prev_open and curr_close > prev_close:
|
||||
signals += 1
|
||||
diff = future_close - curr_close
|
||||
lig_price += diff
|
||||
all_trades.append((f"{i}号", curr["id"], "做多", curr_close, future_close, diff, future["id"]))
|
||||
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
# 前一笔跌 + 反包
|
||||
elif prev_close < prev_open and curr_open < prev_close and curr_close > prev_open:
|
||||
signals += 1
|
||||
diff = future_close - curr_close
|
||||
lig_price += diff
|
||||
all_trades.append((f"{i}号", curr["id"], "做多", curr_close, future_close, diff, future["id"]))
|
||||
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
# 当前为跌
|
||||
elif curr_close < curr_open:
|
||||
# 前一笔跌 + 包裹
|
||||
if prev_close < prev_open and curr_open > prev_open and curr_close < prev_close:
|
||||
signals += 1
|
||||
diff = curr_close - future_close
|
||||
low_price += diff
|
||||
all_trades.append((f"{i}号", curr["id"], "做空", curr_close, future_close, diff, future["id"]))
|
||||
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
# 前一笔涨 + 反包
|
||||
elif prev_close > prev_open and curr_open > prev_close and curr_close < prev_open:
|
||||
signals += 1
|
||||
diff = curr_close - future_close
|
||||
low_price += diff
|
||||
all_trades.append((f"{i}号", curr["id"], "做空", curr_close, future_close, diff, future["id"]))
|
||||
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
if signals > 0:
|
||||
logger.info(
|
||||
f"日期:{i}号,信号数={signals}, 胜率={wins / signals * 100:.2f}%,上涨方向:{lig_price:.2f},下跌方向:{low_price:.2f},综合价格:{(lig_price + low_price):.2f}"
|
||||
)
|
||||
else:
|
||||
logger.info(f"日期:{i}号,没有信号")
|
||||
|
||||
zh_project += (lig_price + low_price)
|
||||
|
||||
logger.success(f"综合价格:{zh_project:.2f}")
|
||||
|
||||
# 输出每笔交易
|
||||
logger.info("===== 每笔交易详情 =====")
|
||||
|
||||
n = 0
|
||||
n1 = 0
|
||||
for trade in all_trades:
|
||||
date, time_str, direction, entry, exit, diff, end_time = trade
|
||||
|
||||
# logger.info(f"{date} {direction} 入场={entry:.2f} 出场={exit:.2f} 差价={diff:.2f} 盈利:{diff / entry * 10000}")
|
||||
logger.info(
|
||||
f"{date} {time_str} {direction} 入场={entry:.2f} 出场={exit:.2f} 出场时间:{end_time} 差价={diff:.2f} 盈利:{diff / entry * 10000} 开仓手续费:5u 平仓手续费:{10000 / entry * exit * 0.0005}"
|
||||
)
|
||||
])
|
||||
|
||||
# 添加信号点
|
||||
fig.add_trace(go.Scatter(
|
||||
x=signal_times,
|
||||
y=signal_prices,
|
||||
mode="markers",
|
||||
marker=dict(color="red", size=10, symbol="triangle-up"),
|
||||
name="做多信号"
|
||||
))
|
||||
# 手续费率是在 0.06%
|
||||
# 开仓手续费
|
||||
# 平仓手续费
|
||||
# 10000 / entry * exit * 0.0006
|
||||
|
||||
fig.update_layout(
|
||||
title="ETH-USDT 1分钟K线图 (含做多信号)",
|
||||
xaxis_title="时间",
|
||||
yaxis_title="价格",
|
||||
xaxis_rangeslider_visible=False,
|
||||
template="plotly_dark"
|
||||
)
|
||||
n1 += 5 + (10000 / entry * exit * 0.0005)
|
||||
|
||||
fig.show()
|
||||
n += ((diff / entry) * 10000)
|
||||
|
||||
print(len(all_trades))
|
||||
print(n)
|
||||
print(n1)
|
||||
|
||||
134
回测数据/test2.py
Normal file
134
回测数据/test2.py
Normal file
@@ -0,0 +1,134 @@
|
||||
import datetime
|
||||
import requests
|
||||
from loguru import logger
|
||||
|
||||
headers = {
|
||||
'accept': 'application/json, text/plain, */*',
|
||||
'accept-language': 'zh,zh-CN;q=0.9,zh-HK;q=0.8,en;q=0.7',
|
||||
'cache-control': 'no-cache',
|
||||
'origin': 'https://www.websea.com',
|
||||
'pragma': 'no-cache',
|
||||
'priority': 'u=1, i',
|
||||
'referer': 'https://www.websea.com/',
|
||||
'sec-ch-ua': '"Chromium";v="140", "Not=A?Brand";v="24", "Google Chrome";v="140"',
|
||||
'sec-ch-ua-mobile': '?0',
|
||||
'sec-ch-ua-platform': '"Windows"',
|
||||
'sec-fetch-dest': 'empty',
|
||||
'sec-fetch-mode': 'cors',
|
||||
'sec-fetch-site': 'same-site',
|
||||
'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/140.0.0.0 Safari/537.36',
|
||||
}
|
||||
|
||||
|
||||
def fetch_kline(day: int):
|
||||
"""获取某一天的分钟K线数据"""
|
||||
time_ser = datetime.datetime(2025, 9, day)
|
||||
start_of_day = time_ser.replace(hour=0, minute=0, second=0, microsecond=0)
|
||||
end_of_day = time_ser.replace(hour=23, minute=59, second=59, microsecond=0)
|
||||
params = {
|
||||
'symbol': 'ETH-USDT',
|
||||
'period': '1min',
|
||||
'start': int(start_of_day.timestamp()),
|
||||
'end': int(end_of_day.timestamp()),
|
||||
}
|
||||
response = requests.get('https://capi.websea.com/webApi/market/getKline', params=params, headers=headers)
|
||||
data = response.json()['result']['data']
|
||||
return sorted(data, key=lambda x: x['id'])
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
zh_project = 0
|
||||
all_trades = [] # 存放所有交易记录
|
||||
|
||||
for i in range(30, 31):
|
||||
|
||||
sorted_data = fetch_kline(i)
|
||||
|
||||
signals = wins = 0
|
||||
lig_price = low_price = 0
|
||||
|
||||
for idx in range(1, len(sorted_data) - 6):
|
||||
prev = sorted_data[idx - 1] # 前一根K
|
||||
curr = sorted_data[idx] # 当前K
|
||||
entry_candle = sorted_data[idx + 1] # ✅ 下一根K线作为开仓点
|
||||
future = sorted_data[idx + 5] # 5根后的K线
|
||||
|
||||
prev_open, prev_close = float(prev['open']), float(prev['close'])
|
||||
curr_open, curr_close = float(curr['open']), float(curr['close'])
|
||||
entry_open = float(entry_candle['open'])
|
||||
future_close = float(future['close'])
|
||||
|
||||
# 当前为涨
|
||||
if curr_close > curr_open:
|
||||
# 前一笔涨 + 包裹
|
||||
if prev_close > prev_open and curr_open < prev_open and curr_close > prev_close:
|
||||
signals += 1
|
||||
diff = future_close - entry_open
|
||||
lig_price += diff
|
||||
all_trades.append((f"{i}号", entry_candle["id"], "做多", entry_open, future_close, diff, future["id"]))
|
||||
|
||||
if future_close > entry_open:
|
||||
wins += 1
|
||||
|
||||
# # 前一笔跌 + 反包
|
||||
# elif prev_close < prev_open and curr_open < prev_close and curr_close > prev_open:
|
||||
# signals += 1
|
||||
# diff = future_close - entry_open
|
||||
# lig_price += diff
|
||||
# all_trades.append((f"{i}号", entry_candle["id"], "做多", entry_open, future_close, diff, future["id"]))
|
||||
#
|
||||
# if future_close > entry_open:
|
||||
# wins += 1
|
||||
#
|
||||
# # 当前为跌
|
||||
# elif curr_close < curr_open:
|
||||
# # 前一笔跌 + 包裹
|
||||
# if prev_close < prev_open and curr_open > prev_open and curr_close < prev_close:
|
||||
# signals += 1
|
||||
# diff = entry_open - future_close
|
||||
# low_price += diff
|
||||
# all_trades.append((f"{i}号", entry_candle["id"], "做空", entry_open, future_close, diff, future["id"]))
|
||||
#
|
||||
# if future_close < entry_open:
|
||||
# wins += 1
|
||||
#
|
||||
# # 前一笔涨 + 反包
|
||||
# elif prev_close > prev_open and curr_open > prev_close and curr_close < prev_open:
|
||||
# signals += 1
|
||||
# diff = entry_open - future_close
|
||||
# low_price += diff
|
||||
# all_trades.append((f"{i}号", entry_candle["id"], "做空", entry_open, future_close, diff, future["id"]))
|
||||
#
|
||||
# if future_close < entry_open:
|
||||
# wins += 1
|
||||
|
||||
if signals > 0:
|
||||
logger.info(
|
||||
f"日期:{i}号,信号数={signals}, 胜率={wins / signals * 100:.2f}%,上涨方向:{lig_price:.2f},下跌方向:{low_price:.2f},综合价格:{(lig_price + low_price):.2f}"
|
||||
)
|
||||
else:
|
||||
logger.info(f"日期:{i}号,没有信号")
|
||||
|
||||
zh_project += (lig_price + low_price)
|
||||
|
||||
logger.success(f"综合价格:{zh_project:.2f}")
|
||||
|
||||
# 输出每笔交易
|
||||
logger.info("===== 每笔交易详情 =====")
|
||||
|
||||
n = n1 = 0
|
||||
for trade in all_trades:
|
||||
date, time_str, direction, entry, exit, diff, end_time = trade
|
||||
|
||||
logger.info(
|
||||
f"{date} {time_str} {direction} 入场={entry:.2f} 出场={exit:.2f} 出场时间:{end_time} 差价={diff:.2f} 盈利:{diff / entry * 10000} "
|
||||
f"开仓手续费:5u 平仓手续费:{10000 / entry * exit * 0.0005}"
|
||||
)
|
||||
|
||||
n1 += 5 + (10000 / entry * exit * 0.0005)
|
||||
n += (diff / entry) * 10000
|
||||
|
||||
print(len(all_trades))
|
||||
print(n)
|
||||
print(n1)
|
||||
@@ -21,7 +21,7 @@ headers = {
|
||||
|
||||
if __name__ == '__main__':
|
||||
# 请求数据
|
||||
time_ser = datetime.datetime(2025, 9, 24)
|
||||
time_ser = datetime.datetime(2025, 9, 22)
|
||||
start_of_day = time_ser.replace(hour=0, minute=0, second=0, microsecond=0)
|
||||
end_of_day = time_ser.replace(hour=23, minute=59, second=59, microsecond=0)
|
||||
params = {
|
||||
@@ -38,6 +38,9 @@ if __name__ == '__main__':
|
||||
signals = 0
|
||||
wins = 0
|
||||
|
||||
lig_price = 0
|
||||
low_price = 0
|
||||
|
||||
for idx in range(1, len(sorted_data) - 2): # 需要至少留两根K线做验证
|
||||
prev = sorted_data[idx - 1] # 前一笔
|
||||
curr = sorted_data[idx] # 当前这笔
|
||||
@@ -52,24 +55,41 @@ if __name__ == '__main__':
|
||||
# 前一笔涨 + 包裹
|
||||
if prev_close > prev_open and curr_open < prev_open and curr_close > prev_close:
|
||||
signals += 1
|
||||
|
||||
lig_price += (future_close - curr_close)
|
||||
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
|
||||
|
||||
# 前一笔跌 + 反包
|
||||
elif prev_close < prev_open and curr_open < prev_close and curr_close > prev_open:
|
||||
signals += 1
|
||||
|
||||
lig_price += (future_close - curr_close)
|
||||
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
|
||||
# 当前为跌
|
||||
elif curr_close < curr_open:
|
||||
# 前一笔跌 + 包裹
|
||||
if prev_close < prev_open and curr_open > prev_open and curr_close < prev_close:
|
||||
signals += 1
|
||||
|
||||
low_price += (curr_close - future_close)
|
||||
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
|
||||
# 前一笔涨 + 反包
|
||||
elif prev_close > prev_open and curr_open > prev_close and curr_close < prev_open:
|
||||
signals += 1
|
||||
|
||||
low_price += (curr_close - future_close)
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
@@ -78,3 +98,6 @@ if __name__ == '__main__':
|
||||
print(f"信号数={signals}, 胜率={win_rate:.2f}%")
|
||||
else:
|
||||
print("没有找到符合条件的形态")
|
||||
|
||||
print(lig_price)
|
||||
print(low_price)
|
||||
|
||||
111
回测数据/接口分析,批量回测数据.py
Normal file
111
回测数据/接口分析,批量回测数据.py
Normal file
@@ -0,0 +1,111 @@
|
||||
import datetime
|
||||
import requests
|
||||
|
||||
from loguru import logger
|
||||
|
||||
headers = {
|
||||
'accept': 'application/json, text/plain, */*',
|
||||
'accept-language': 'zh,zh-CN;q=0.9,zh-HK;q=0.8,en;q=0.7',
|
||||
'cache-control': 'no-cache',
|
||||
'origin': 'https://www.websea.com',
|
||||
'pragma': 'no-cache',
|
||||
'priority': 'u=1, i',
|
||||
'referer': 'https://www.websea.com/',
|
||||
'sec-ch-ua': '"Chromium";v="140", "Not=A?Brand";v="24", "Google Chrome";v="140"',
|
||||
'sec-ch-ua-mobile': '?0',
|
||||
'sec-ch-ua-platform': '"Windows"',
|
||||
'sec-fetch-dest': 'empty',
|
||||
'sec-fetch-mode': 'cors',
|
||||
'sec-fetch-site': 'same-site',
|
||||
'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/140.0.0.0 Safari/537.36',
|
||||
}
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
zh_project = 0
|
||||
|
||||
for i in range(1, 31):
|
||||
|
||||
# 请求数据
|
||||
time_ser = datetime.datetime(2025, 8, i)
|
||||
start_of_day = time_ser.replace(hour=0, minute=0, second=0, microsecond=0)
|
||||
end_of_day = time_ser.replace(hour=23, minute=59, second=59, microsecond=0)
|
||||
params = {
|
||||
'symbol': 'ETH-USDT',
|
||||
'period': '1min',
|
||||
'start': int(start_of_day.timestamp()),
|
||||
'end': int(end_of_day.timestamp()),
|
||||
}
|
||||
|
||||
response = requests.get('https://capi.websea.com/webApi/market/getKline', params=params, headers=headers)
|
||||
data = response.json()['result']['data']
|
||||
sorted_data = sorted(data, key=lambda x: x['id'])
|
||||
|
||||
signals = 0
|
||||
wins = 0
|
||||
|
||||
lig_price = 0
|
||||
low_price = 0
|
||||
|
||||
for idx in range(1, len(sorted_data) - 2): # 需要至少留两根K线做验证
|
||||
prev = sorted_data[idx - 1] # 前一笔
|
||||
curr = sorted_data[idx] # 当前这笔
|
||||
future = sorted_data[idx + 2] # 两根后的K线
|
||||
|
||||
prev_open, prev_close = float(prev['open']), float(prev['close'])
|
||||
curr_open, curr_close = float(curr['open']), float(curr['close'])
|
||||
future_close = float(future['close'])
|
||||
|
||||
# 当前为涨
|
||||
if curr_close > curr_open:
|
||||
# 前一笔涨 + 包裹
|
||||
if prev_close > prev_open and curr_open < prev_open and curr_close > prev_close:
|
||||
signals += 1
|
||||
|
||||
lig_price += (future_close - curr_close)
|
||||
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
# 前一笔跌 + 反包
|
||||
elif prev_close < prev_open and curr_open < prev_close and curr_close > prev_open:
|
||||
signals += 1
|
||||
|
||||
lig_price += (future_close - curr_close)
|
||||
|
||||
if future_close > curr_close:
|
||||
wins += 1
|
||||
|
||||
|
||||
# 当前为跌
|
||||
elif curr_close < curr_open:
|
||||
# 前一笔跌 + 包裹
|
||||
if prev_close < prev_open and curr_open > prev_open and curr_close < prev_close:
|
||||
signals += 1
|
||||
|
||||
low_price += (curr_close - future_close)
|
||||
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
|
||||
# 前一笔涨 + 反包
|
||||
elif prev_close > prev_open and curr_open > prev_close and curr_close < prev_open:
|
||||
signals += 1
|
||||
|
||||
low_price += (curr_close - future_close)
|
||||
if future_close < curr_close:
|
||||
wins += 1
|
||||
|
||||
# if signals > 0:
|
||||
# win_rate = wins / signals * 100
|
||||
# print(f"信号数={signals}, 胜率={win_rate:.2f}%")
|
||||
# else:
|
||||
# print("没有找到符合条件的形态")
|
||||
|
||||
logger.info(
|
||||
f"日期:{i}号,信号数={signals}, 胜率={wins / signals * 100:.2f}%,上涨方向:{lig_price:.2f},下跌方向:{low_price:.2f},综合价格:{(lig_price - low_price):.2f}")
|
||||
|
||||
zh_project += (lig_price - low_price)
|
||||
|
||||
logger.success(f"综合价格:{zh_project:.2f}")
|
||||
Reference in New Issue
Block a user