def _exit_by_max_holding_time( trades: Trades, df: pd.DataFrame, max_holding_time: pd.Timedelta, exit_condition: Callable[[pd.DataFrame, pd.Series, pd.Timestamp], bool], ) -> Trades: indices = [] # type: List[pd.Timestamp] exits = [] # type: List[Tuple[float, int]] for i in trades.ids: trade = trades.get_trade(i) if trade.sum() == 0: continue idx = trade.index[0] start = max(idx, df.index[0]) end = min(idx + max_holding_time, df.index[-1]) df_exit = df.loc[start:end] transaction = _exit_transaction(df_exit, trade, exit_condition) indices.append(transaction.timestamp) exits.append((transaction.amount, i)) df = pd.DataFrame(index=indices, data=exits, columns=["amount", "_id"]) return from_dataframe(df, symbol, currency_unit)
def count_trades(trades: Trades, mkt: MarketData) -> Tuple[int, int, int]: """Count winning, losing and total number of trades. Args: trades : Trades to evaluate. Each trade is evaluated only if it contains more than one transactions, because we can define pl in that case. mkt: Market data. The index should contains all trades' index. Returns: total count, win count, lose count """ pls = [ _calc_pl(trades.get_trade(i), mkt) for i in trades.ids if len(trades.get_trade(i).index) > 1 ] total = len(trades.ids) win = sum([pl > 0.0 for pl in pls]) lose = sum([pl < 0.0 for pl in pls]) return total, win, lose
def skip_entry_by_hours(trades: Trades, hours: List[int]) -> Trades: """Skip entry by hours. Args: trades: Trades hours: Hours which will be filtered out from entry. Result: Trades """ deleted_ids = [] for i in trades.ids: entry = trades.get_trade(i).index[0] if entry.hour in hours: deleted_ids.append(i) return trades[~trades["_id"].isin(deleted_ids)]
def skip_entry_by_spread(trades: Trades, mkt: AskBidMarketData, max_spread: float) -> Trades: """Skip entry by spread. Args: trades: Trades mkt: Market data for ask/bid prices max_spread: More than the value, skip entry Result: Trades """ assert max_spread >= 0.0 assert trades.index.unique().isin(mkt.index).all() spread = mkt.spread deleted_ids = [] # type: List[int] for i in trades.ids: entry = trades.get_trade(i).index[0] if spread.at[entry] > max_spread: deleted_ids.append(i) return trades[~trades["_id"].isin(deleted_ids)]
def _exit( trades: Trades, df: pd.DataFrame, exit_condition: Callable[[pd.DataFrame, pd.Series], pd.Series], ) -> pd.Series: indices = [] # type: List[pd.Timestamp] exits = [] # type: List[Tuple[float, int]] for i in trades.ids: trade = trades.get_trade(i) if trade.sum() == 0: continue idx = trade.index[0] df_exit = df[idx <= df.index] transaction = _exit_transaction(df_exit, trade, exit_condition) indices.append(transaction.timestamp) exits.append((transaction.amount, i)) df = pd.DataFrame(index=indices, data=exits, columns=["amount", "_id"]) return from_dataframe(df, symbol)