
使用Hummingbot Script开发策略系列之七:马丁格尔策略
在本篇博客中,我们将介绍如何使用Hummingbot Script开发一个马丁格尔策略。什么是马丁格尔策略马丁格尔,英文名称Martingale或缩写MG(Martigues是或曾经是法国的一个村庄,最早的时候马丁格尔应该是指马身上用于控制马车的马具),是一种基于18世纪流行于法国的赌博方式的交易策略。它在赌场游戏系统中盛行至今,是一种著名的策略,被称为“永远不亏钱的马丁格尔”。 马丁格尔策略的操作准则很简单:在任何一张可以买大小(单双)的赌桌上,你从一单位赌注开始,在每次输钱后,将赌注加倍,而在任何一次赢钱后,下一次又回归到一单位赌注。因此,无论你在赢钱之前输了多少次,只要概率让你赢一次,你就能够收回先前的损失,并且还会获得第一次赌注总额的收益。 马丁格尔策略最初用于赌场,后来移植到金融交易市场中,创造了许多盈利奇迹,但更多的是爆仓破产的消息。马丁格尔策略的优缺点可以说是对立的,因为它们都与该策略最根本的理论依据相关:认为行情永远会回调。尽管这种观点在非常大的时间跨度上来说或许是正确的,然而真实的市场情况远比这复杂,价格行情既不是随机的,交易者也不可能有无限的资金。因此,马丁格...
Binance交易所在AWS不同区域的延迟分析
[本文由Hummingbot社区成员vik投稿] 如果你对加密货币交易感兴趣,你可能知道服务器位置在交易速度和效率方面可以起到决定性作用。几年前,我尝试了解更多关于这个主题的信息,但当时信息有限。因此,我自己进行了一些研究。随着时间的推移,深入分析的需求变得显而易见,我认为有必要分享这些见解。 我从Binance开始,但我计划很快研究其他交易平台。研究方法我使用Hummingbot来运行测试。作为一个包罗万象的开源解决方案,它配备了多个交换连接器。它还易于用户创建加密货币交易机器人,只需一个 Python 脚本即可实现 主要目标不是找到确切的延迟时间,而是确定最佳的AWS区域。为了实现这一目标,我设计了一个简单的Hummingbot脚本,用于比较订单创建、取消和执行的时间持续时间。时间戳:对于每个订单(无论是创建、取消还是执行),脚本都会记录两个时间戳以及订单ID,保存在CSV文件中。传输前时间戳:这标志着在API请求发送到交易所之前的时间。传输后时间戳:这是从交易所收到成功确认的时间。By analyzing the difference between the pre-tra...
使用Hummingbot Script移植韭菜收割机策略(3)
接上回,这节讲一下机器人的绩效和改进思路, 话不多说,直接上图:与原作者和众多移植版本的结果差不多:成交量大,日成交量大约是总资金的100倍平均买入价和卖出价基本相等,趋势策略在这个BTC-USDT这个竞争激烈的市场基本不赚钱手续费(0.1%)比利润高得多,正如原作者所说,原版的韭菜收割机已经不适合当前的市场了。尽管如此,我们还是有一些方法能优化这个策略:用合约代替现货,减少融币和代码中平衡资产的环节用maker 取代 taker进行买入(开仓)操作调整优化参数,例如爆发百分比,tick间隔时间使用hummingbot内建方法重写获取交易量模块找到手续费更合适的市场进行交易,如果手续费是(-0.01%),那么这个策略将会是一个可以盈利的策略。如有任何问题获想参与讨论,请加入我们的社区我们的社区有众多的做市商和套利者,他们愿意互相帮助,充分利用 Hummingbot。 您可以加入我们的 Discord 中文频道,讨论 Hummingbot、策略、流动性挖坑以及与加密货币世界有关的任何其他内容,并获得我们团队的直接支持。 加入中文微信群,请添加ID:amtf202004 https:...
Community Manager & Solution Consultant @hummingbot

使用Hummingbot Script开发策略系列之七:马丁格尔策略
在本篇博客中,我们将介绍如何使用Hummingbot Script开发一个马丁格尔策略。什么是马丁格尔策略马丁格尔,英文名称Martingale或缩写MG(Martigues是或曾经是法国的一个村庄,最早的时候马丁格尔应该是指马身上用于控制马车的马具),是一种基于18世纪流行于法国的赌博方式的交易策略。它在赌场游戏系统中盛行至今,是一种著名的策略,被称为“永远不亏钱的马丁格尔”。 马丁格尔策略的操作准则很简单:在任何一张可以买大小(单双)的赌桌上,你从一单位赌注开始,在每次输钱后,将赌注加倍,而在任何一次赢钱后,下一次又回归到一单位赌注。因此,无论你在赢钱之前输了多少次,只要概率让你赢一次,你就能够收回先前的损失,并且还会获得第一次赌注总额的收益。 马丁格尔策略最初用于赌场,后来移植到金融交易市场中,创造了许多盈利奇迹,但更多的是爆仓破产的消息。马丁格尔策略的优缺点可以说是对立的,因为它们都与该策略最根本的理论依据相关:认为行情永远会回调。尽管这种观点在非常大的时间跨度上来说或许是正确的,然而真实的市场情况远比这复杂,价格行情既不是随机的,交易者也不可能有无限的资金。因此,马丁格...
Binance交易所在AWS不同区域的延迟分析
[本文由Hummingbot社区成员vik投稿] 如果你对加密货币交易感兴趣,你可能知道服务器位置在交易速度和效率方面可以起到决定性作用。几年前,我尝试了解更多关于这个主题的信息,但当时信息有限。因此,我自己进行了一些研究。随着时间的推移,深入分析的需求变得显而易见,我认为有必要分享这些见解。 我从Binance开始,但我计划很快研究其他交易平台。研究方法我使用Hummingbot来运行测试。作为一个包罗万象的开源解决方案,它配备了多个交换连接器。它还易于用户创建加密货币交易机器人,只需一个 Python 脚本即可实现 主要目标不是找到确切的延迟时间,而是确定最佳的AWS区域。为了实现这一目标,我设计了一个简单的Hummingbot脚本,用于比较订单创建、取消和执行的时间持续时间。时间戳:对于每个订单(无论是创建、取消还是执行),脚本都会记录两个时间戳以及订单ID,保存在CSV文件中。传输前时间戳:这标志着在API请求发送到交易所之前的时间。传输后时间戳:这是从交易所收到成功确认的时间。By analyzing the difference between the pre-tra...
使用Hummingbot Script移植韭菜收割机策略(3)
接上回,这节讲一下机器人的绩效和改进思路, 话不多说,直接上图:与原作者和众多移植版本的结果差不多:成交量大,日成交量大约是总资金的100倍平均买入价和卖出价基本相等,趋势策略在这个BTC-USDT这个竞争激烈的市场基本不赚钱手续费(0.1%)比利润高得多,正如原作者所说,原版的韭菜收割机已经不适合当前的市场了。尽管如此,我们还是有一些方法能优化这个策略:用合约代替现货,减少融币和代码中平衡资产的环节用maker 取代 taker进行买入(开仓)操作调整优化参数,例如爆发百分比,tick间隔时间使用hummingbot内建方法重写获取交易量模块找到手续费更合适的市场进行交易,如果手续费是(-0.01%),那么这个策略将会是一个可以盈利的策略。如有任何问题获想参与讨论,请加入我们的社区我们的社区有众多的做市商和套利者,他们愿意互相帮助,充分利用 Hummingbot。 您可以加入我们的 Discord 中文频道,讨论 Hummingbot、策略、流动性挖坑以及与加密货币世界有关的任何其他内容,并获得我们团队的直接支持。 加入中文微信群,请添加ID:amtf202004 https:...
Community Manager & Solution Consultant @hummingbot
Share Dialog
Share Dialog

Subscribe to Dolm

Subscribe to Dolm
<100 subscribers
<100 subscribers
根据我们在上一节的设计流程图可以看出,我们需要写几个主要函数来实现功能:
更新交易量
更新订单簿
平衡资产
判断市场状况并下单
万事开头难,第一步我们就遇到了问题,因为Hummingbot Script并没有提供直接获取历史交易的方法,
我们只能直接用交易所的API去获取这个数据,不过据说Hummingbot的开发人员已经在着手写一个和Trade相关的模块,以便让用户更方便地调用:
def update_vols(self):
trades = pd.DataFrame(self.fetch_historical_trades(self.trading_pair, 15))
self.vol = 0.7*self.vol+0.3*trades.size.sum()
if len(self.prices) == 0:
self.prices = list(trades['price'].astype('float'))
def fetch_historical_trades(self, trading_pair: str, limit) -> List[Decimal]:
url = "https://api.binance.com/api/v3/trades"
params = {
"symbol": trading_pair.replace("-", ""),
"limit": f"{limit}"
}
trades = requests.get(url=url, params=params).json()
return trades
这段程序实现了以下功能:update_vols()函数中,使用pd.DataFrame(self.fetch_historical_trades(self.trading_pair, 15))获取近15条交易的信息,存储在trades变量中。使用trades.size.sum()获取trades中交易数量的总和,并使用0.7self.vol+0.3trades.size.sum()更新self.vol的值。判断self.prices列表是否为空,如果为空,将trades中price列转化为浮点数后存储在self.prices中。fetch_historical_trades()函数中,使用requests.get(url=url, params=params).json()获取最近15条交易的信息。其中url是API的URL,params是请求参数,包括交易对和交易数量。最后返回获取到的交易信息。注意:这段代码与Binance交易所相关,需要确保你有Binance的API访问权限。
Hummingbot有一个获取订单薄的方法,我们可以直接使用:
def update_orderBooks(self):
orderBook = self.connectors[self.connector_name].get_order_book(self.trading_pair)
ask_entries = orderBook.ask_entries()
bid_entries = orderBook.bid_entries()
Asks1 = float(next(ask_entries).price)
Asks2 = float(next(ask_entries).price)
Asks3 = float(next(ask_entries).price)
Bids1 = float(next(bid_entries).price)
Bids2 = float(next(bid_entries).price)
Bids3 = float(next(bid_entries).price)
Asks = Bids1*0.618 + Asks1*0.382 + 0.01
Bids = Bids1*0.382 + Asks1*0.618 - 0.01
PriceGetIn = (Bids1+Asks1)*0.35 + (Bids2+Asks2)*0.1 + (Bids3+Asks3)*0.05
self.prices.pop(0)
self.prices.append(PriceGetIn)
return Asks,Bids,Asks1,Bids1
这段程序实现了以下功能:使用self.connectors[self.connector_name].get_order_book(self.trading_pair)获取交易对的订单簿。使用ask_entries()和bid_entries()方法分别获取卖盘和买盘的订单。使用next(ask_entries).price和next(bid_entries).price获取卖盘和买盘的价格。其中Asks1, Asks2, Asks3, Bids1, Bids2, Bids3分别表示第一第二第三档卖盘和买盘的价格。使用Asks1和Bids1算出Asks和Bids的值。使用Bids1, Asks1, Bids2, Asks2, Bids3, Asks3算出PriceGetIn的值。将PriceGetIn的值加入self.prices列表中。最后返回Asks, Bids, Asks1, Bids1四个值。注意:程序中的0.618,0.382,0.01和0.35,0.1,0.05是预先设定的常量,他们对于程序的结果有影响。
def get_balance(self):
df = self.get_balance_df()
self.base_asset = float(df.loc[df['Asset'] == self.base, 'Total Balance'])
self.price = float(self.connectors[self.connector_name].get_mid_price(self.trading_pair))
self.base_value = self.base_asset * self.price
self.quote_asset = float(df.loc[df['Asset'] == self.quote, 'Total Balance'])
total_value = self.quote_asset + self.base_value
if self.base_value >= total_value * 0.52:
self.sell(self.connector_name, self.trading_pair, Decimal(total_value/self.price * self.threshold),
OrderType.LIMIT, Decimal(self.price * 1.0001))
elif self.base_value < total_value * 0.48:
self.buy(self.connector_name, self.trading_pair, Decimal(total_value/self.price * self.threshold),
OrderType.LIMIT, Decimal(self.price * 0.9999))
这段程序实现了以下功能:1.使用self.get_balance_df()获取账户资产信息并存储在df中。2.使用df.loc[df['Asset'] == self.base, 'Total Balance']获取基准资产的余额并存储在self.base_asset中。3.使用self.connectors[self.connector_name].get_mid_price(self.trading_pair)获取基准资产和报价资产的中间价格,并存储在self.price中。使用self.base_asset * self.price计算基准资产的总价值并存储在self.base_value中。使用df.loc[df['Asset'] == self.quote, 'Total Balance']获取报价资产的余额并存储在self.quote_asset中。使用self.quote_asset + self.base_value计算总价值并存储在total_value中。判断基准资产的总价值是否大于等于总价值的52%,如果是,调用self.sell()函数卖出指定比例的资产;如果基准资产的总价值小于总价值的48%,调用self.buy()函数买入指定比例的资产。注意:程序中使用了self.connector_name,self.trading_pair,self.threshold,self.base,self.quote等变量,需要确保这些变量已经被正确赋值。
这一部分的代码比较长,就不贴出来了,简单说就是通过定义好的爆发阈值判断当前市场是牛市或者是熊市,并根据交易量、价格波动、盘口价差等因素进行下单力度调整,具体可以原始代码。
最后我们在on_tick函数中调用上面几个函数,程序就基本完成了。
下一节,我们将展示实际的机器人绩效,并提出一些优化改进的想法。
我们的社区有众多的做市商和套利者,他们愿意互相帮助,充分利用 Hummingbot。 您可以加入我们的 Discord 中文频道
,讨论 Hummingbot、策略、流动性挖坑以及与加密货币世界有关的任何其他内容,并获得我们团队的直接支持。
加入中文微信群,请添加ID:amtf202004
根据我们在上一节的设计流程图可以看出,我们需要写几个主要函数来实现功能:
更新交易量
更新订单簿
平衡资产
判断市场状况并下单
万事开头难,第一步我们就遇到了问题,因为Hummingbot Script并没有提供直接获取历史交易的方法,
我们只能直接用交易所的API去获取这个数据,不过据说Hummingbot的开发人员已经在着手写一个和Trade相关的模块,以便让用户更方便地调用:
def update_vols(self):
trades = pd.DataFrame(self.fetch_historical_trades(self.trading_pair, 15))
self.vol = 0.7*self.vol+0.3*trades.size.sum()
if len(self.prices) == 0:
self.prices = list(trades['price'].astype('float'))
def fetch_historical_trades(self, trading_pair: str, limit) -> List[Decimal]:
url = "https://api.binance.com/api/v3/trades"
params = {
"symbol": trading_pair.replace("-", ""),
"limit": f"{limit}"
}
trades = requests.get(url=url, params=params).json()
return trades
这段程序实现了以下功能:update_vols()函数中,使用pd.DataFrame(self.fetch_historical_trades(self.trading_pair, 15))获取近15条交易的信息,存储在trades变量中。使用trades.size.sum()获取trades中交易数量的总和,并使用0.7self.vol+0.3trades.size.sum()更新self.vol的值。判断self.prices列表是否为空,如果为空,将trades中price列转化为浮点数后存储在self.prices中。fetch_historical_trades()函数中,使用requests.get(url=url, params=params).json()获取最近15条交易的信息。其中url是API的URL,params是请求参数,包括交易对和交易数量。最后返回获取到的交易信息。注意:这段代码与Binance交易所相关,需要确保你有Binance的API访问权限。
Hummingbot有一个获取订单薄的方法,我们可以直接使用:
def update_orderBooks(self):
orderBook = self.connectors[self.connector_name].get_order_book(self.trading_pair)
ask_entries = orderBook.ask_entries()
bid_entries = orderBook.bid_entries()
Asks1 = float(next(ask_entries).price)
Asks2 = float(next(ask_entries).price)
Asks3 = float(next(ask_entries).price)
Bids1 = float(next(bid_entries).price)
Bids2 = float(next(bid_entries).price)
Bids3 = float(next(bid_entries).price)
Asks = Bids1*0.618 + Asks1*0.382 + 0.01
Bids = Bids1*0.382 + Asks1*0.618 - 0.01
PriceGetIn = (Bids1+Asks1)*0.35 + (Bids2+Asks2)*0.1 + (Bids3+Asks3)*0.05
self.prices.pop(0)
self.prices.append(PriceGetIn)
return Asks,Bids,Asks1,Bids1
这段程序实现了以下功能:使用self.connectors[self.connector_name].get_order_book(self.trading_pair)获取交易对的订单簿。使用ask_entries()和bid_entries()方法分别获取卖盘和买盘的订单。使用next(ask_entries).price和next(bid_entries).price获取卖盘和买盘的价格。其中Asks1, Asks2, Asks3, Bids1, Bids2, Bids3分别表示第一第二第三档卖盘和买盘的价格。使用Asks1和Bids1算出Asks和Bids的值。使用Bids1, Asks1, Bids2, Asks2, Bids3, Asks3算出PriceGetIn的值。将PriceGetIn的值加入self.prices列表中。最后返回Asks, Bids, Asks1, Bids1四个值。注意:程序中的0.618,0.382,0.01和0.35,0.1,0.05是预先设定的常量,他们对于程序的结果有影响。
def get_balance(self):
df = self.get_balance_df()
self.base_asset = float(df.loc[df['Asset'] == self.base, 'Total Balance'])
self.price = float(self.connectors[self.connector_name].get_mid_price(self.trading_pair))
self.base_value = self.base_asset * self.price
self.quote_asset = float(df.loc[df['Asset'] == self.quote, 'Total Balance'])
total_value = self.quote_asset + self.base_value
if self.base_value >= total_value * 0.52:
self.sell(self.connector_name, self.trading_pair, Decimal(total_value/self.price * self.threshold),
OrderType.LIMIT, Decimal(self.price * 1.0001))
elif self.base_value < total_value * 0.48:
self.buy(self.connector_name, self.trading_pair, Decimal(total_value/self.price * self.threshold),
OrderType.LIMIT, Decimal(self.price * 0.9999))
这段程序实现了以下功能:1.使用self.get_balance_df()获取账户资产信息并存储在df中。2.使用df.loc[df['Asset'] == self.base, 'Total Balance']获取基准资产的余额并存储在self.base_asset中。3.使用self.connectors[self.connector_name].get_mid_price(self.trading_pair)获取基准资产和报价资产的中间价格,并存储在self.price中。使用self.base_asset * self.price计算基准资产的总价值并存储在self.base_value中。使用df.loc[df['Asset'] == self.quote, 'Total Balance']获取报价资产的余额并存储在self.quote_asset中。使用self.quote_asset + self.base_value计算总价值并存储在total_value中。判断基准资产的总价值是否大于等于总价值的52%,如果是,调用self.sell()函数卖出指定比例的资产;如果基准资产的总价值小于总价值的48%,调用self.buy()函数买入指定比例的资产。注意:程序中使用了self.connector_name,self.trading_pair,self.threshold,self.base,self.quote等变量,需要确保这些变量已经被正确赋值。
这一部分的代码比较长,就不贴出来了,简单说就是通过定义好的爆发阈值判断当前市场是牛市或者是熊市,并根据交易量、价格波动、盘口价差等因素进行下单力度调整,具体可以原始代码。
最后我们在on_tick函数中调用上面几个函数,程序就基本完成了。
下一节,我们将展示实际的机器人绩效,并提出一些优化改进的想法。
我们的社区有众多的做市商和套利者,他们愿意互相帮助,充分利用 Hummingbot。 您可以加入我们的 Discord 中文频道
,讨论 Hummingbot、策略、流动性挖坑以及与加密货币世界有关的任何其他内容,并获得我们团队的直接支持。
加入中文微信群,请添加ID:amtf202004
No activity yet