Ý tưởng chính của chiến lược này là mô phỏng giao dịch trong thời gian thực, thu thập dữ liệu giao dịch hàng tuần và hiển thị các kết quả thống kê dưới dạng bảng để có thể xem xét trực quan hơn về hoạt động của chiến lược. Nó giúp chúng ta nhanh chóng đánh giá chiến lược, xác định thời gian chiến lược không hoạt động tốt, và điều chỉnh và tối ưu hóa chiến lược theo đó.
Thiết lập thời gian bắt đầu và kết thúc chu kỳ tính toán.
Thiết lập độ chính xác của kết quả thống kê và số tuần trong mỗi nhóm.
Các chiến lược mua bán bắt chước RSI.
Định nghĩa các biến trong bảng thống kê.
Tính toán kết quả của chu kỳ hiện tại.
Nếu chu kỳ thay đổi và cho phép giao dịch, ghi lại thời gian và kết quả của chu kỳ này.
Nếu là dòng K cuối cùng và cho phép giao dịch, ghi lại thời gian và kết quả của chu kỳ hiện tại.
Nếu chu kỳ thay đổi và không cho phép giao dịch, ghi lại thời gian và kết quả của chu kỳ trước.
Tìm kết quả chu kỳ cao nhất và thấp nhất.
Những con số này có thể được sử dụng trong các hình ảnh.
Đầu tiên tính tổng số chu kỳ thống kê
Đi qua mỗi chu kỳ, biểu diễn các trang, thời gian và kết quả
Kết quả của mỗi nhóm chu kỳ được tích lũy
Kết quả dương tính được đánh dấu bằng màu sắc
Có thể xem kết quả giao dịch hàng tuần trong thời gian thực và đánh giá nhanh hiệu suất chiến lược
Những kết quả hiển thị trực quan, ngay lập tức, giúp bạn tìm ra các chu kỳ chiến lược hoạt động kém.
Có thể điều chỉnh và tối ưu hóa các tham số chiến lược theo mức lợi nhuận và thua lỗ trong khoảng thời gian
Có thể dễ dàng theo dõi lợi nhuận tích lũy hàng tuần từ chiến lược nắm giữ dài hạn
Có thể phân tích các phong cách giao dịch khác nhau trong thời gian
Tính chính xác thống kê tùy chỉnh và số tuần phân nhóm để đáp ứng nhu cầu khác nhau
Mã thực hiện đơn giản, rõ ràng, dễ hiểu và phát triển thứ hai
Chiến lược này dựa trên RSI để kinh doanh giả lập, và chiến lược RSI có những nhược điểm của nó không theo xu hướng đủ mạnh.
Trong thực tế, chi phí giao dịch có ảnh hưởng lớn đến kết quả.
Dữ liệu lịch sử được sử dụng để đánh giá lại không nhất thiết phản ánh môi trường giao dịch thực tế
Kết quả thống kê phụ thuộc vào số tiền trong tài khoản thực, số tiền mặc định trong đánh giá lại không nhất thiết chính xác
Cần chú ý để ngăn ngừa quá phù hợp, thay đổi một cách mù quáng các tham số chính sách theo kết quả kiểm tra lại
Có thể tăng cường chiến lược RSI bằng cách kết hợp nhiều chỉ số hơn để xác định xu hướng, tối ưu hóa các điểm vào và ra. Khi giao dịch trên thực tế, hãy chú ý đến việc thiết lập phí thủ tục theo các tham số thực sự. Tăng sự biến động của số tiền trong giai đoạn kiểm tra lại, làm cho nó gần với thực tế hơn, v.v.
Bạn có thể xem xét sử dụng logic dừng lỗ để kiểm soát lỗ đơn lẻ.
Có thể tối ưu hóa các thông số chiến lược như điều chỉnh ngưỡng tăng hoặc giảm của RSI
Có thể thử các tần số giao dịch khác nhau, chẳng hạn như giao dịch trong ngày hoặc giữ hàng tháng
Có thể thêm nhiều chỉ số để xác định xu hướng thị trường và thời điểm tham gia
Bạn có thể xem xét thêm logic ngăn chặn.
Bạn có thể tối ưu hóa cài đặt các thông số thống kê
Có thể xem xét thực hiện thống kê về nhiều loại tài sản
Bằng cách thêm stop-loss, bạn có thể kiểm soát tốt hơn tỷ lệ rủi ro và lợi nhuận. Tối ưu hóa các thông số RSI có thể cải thiện tỷ lệ thắng. Sử dụng nhiều thông số hơn và tần suất giao dịch khác nhau có thể làm cho chiến lược ổn định hơn. Điều chỉnh các thông số thống kê có thể làm cho kết quả nổi bật hơn.
Mục đích của chiến lược là thu thập kết quả giao dịch theo chu kỳ, hiển thị trực quan dưới dạng bảng thống kê, để có thể nhanh chóng xác định tình trạng thua lỗ của chiến lược trong các khoảng thời gian khác nhau. Điều này cung cấp hỗ trợ dữ liệu cho tối ưu hóa chiến lược. Ưu điểm là có thể xem kết quả hàng tuần trong thời gian thực, trực quan rõ ràng và dễ phát triển thứ hai.
/*backtest start: 2023-09-12 00:00:00 end: 2023-10-12 00:00:00 period: 3h basePeriod: 15m exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}] */ //@version=5 // strategy('Strategy weekly results as numbers v1', overlay=true, default_qty_type=strategy.percent_of_equity, default_qty_value=25, commission_type=strategy.commission.percent, commission_value=0.04) after = input(title='Trade after', defval=timestamp('01 Jan 2019 00:00 UTC'), tooltip="Strategy will be executed after this timestamp. The statistic table will include only periods after this date.") before = input(title='Trade before', defval=timestamp('31 Dec 2024 23:59 UTC'), tooltip="Strategy will be executes before this timestamp. The statistic table will include only periods before this date.") statisticPrecision = input.int(title='Statistic precision', group='Statistic visualisation', defval=1, tooltip="Defines how many digits should be rendered in every statistic cell.") statisticGroupSize = input.int(title='Statistic group size', group='Statistic visualisation', defval=12, tooltip="Defines how many cells should be in one group inside the statistic table.") // determinet whether the starategy should be traded between the period isTradeEnabled = true // ******************************************************************************************* // Core strategy simulation logic // ******************************************************************************************* // calculate rsi strategy emulation data rsiEmulationData = ta.rsi(close, 7) rsiEmulationCrossover = ta.crossover(rsiEmulationData, 70) rsiEmulationCrossunder = ta.crossunder(rsiEmulationData, 30) // entry loogic based on the rsi calculations if (isTradeEnabled and rsiEmulationCrossover) strategy.entry('Long', strategy.long) if (isTradeEnabled and rsiEmulationCrossunder) strategy.entry('Short', strategy.short) // ******************************************************************************************* // Weekly statistics table // ******************************************************************************************* // define statistic variables var statisticTable = table(na) var statisticPeriodTime = array.new_int(0) var statisticPeriodResult = array.new_float(0) var statisticIsLatestCalculated = bool(na) var statisticResultHighest = float(na) var statisticResultLowest = float(na) var statisticColorGray = color.new(color.gray, transp = 60) var statisticColorGreen = color.new(color.green, transp = 60) var statisticColorRed = color.new(color.red, transp = 60) // claculate current period result barResult = not na(strategy.equity[1]) ? (strategy.equity / strategy.equity[1] - 1) : 0 isPeriodChanged = not na(time[1]) and weekofyear(time) != weekofyear(time[1]) currentPeriodResult = 0.0 currentPeriodResult := not na(currentPeriodResult[1]) and not isPeriodChanged ? ((1 + currentPeriodResult[1]) * (1 + barResult) - 1) : 0.0 // initialise highest and lowest results variables statisticResultHighest := na(statisticResultHighest) ? currentPeriodResult : statisticResultHighest statisticResultLowest := na(statisticResultLowest) ? currentPeriodResult : statisticResultLowest // search for highest and lowest results statisticResultHighest := currentPeriodResult > statisticResultHighest ? currentPeriodResult : statisticResultHighest statisticResultLowest := currentPeriodResult < statisticResultLowest ? currentPeriodResult : statisticResultLowest // new week while trade is active if isPeriodChanged and isTradeEnabled timeCalculated = time - 1000 * 60 * 60 * 24 * 7 resultCalculated = currentPeriodResult[1] statisticIsLatestCalculated := false array.push(statisticPeriodTime, timeCalculated) array.push(statisticPeriodResult, resultCalculated) // latest bar while trade is active if barstate.islast and isTradeEnabled timeCalculated = time - 1000 * 60 * 60 * 24 * (dayofweek(time) - 2) resultCalculated = currentPeriodResult array.push(statisticPeriodTime, timeCalculated) array.push(statisticPeriodResult, resultCalculated) // new week after trade disabled if isPeriodChanged and not isTradeEnabled and not na(statisticIsLatestCalculated) and not statisticIsLatestCalculated timeCalculated = time - 1000 * 60 * 60 * 24 * (dayofweek(time) + 5) resultCalculated = currentPeriodResult[1] statisticIsLatestCalculated := true array.push(statisticPeriodTime, timeCalculated) array.push(statisticPeriodResult, resultCalculated) // render statistics table if barstate.islast statisticLength = array.size(statisticPeriodResult) statisticTableSteps = math.floor(statisticLength / statisticGroupSize) + (statisticLength % statisticGroupSize != 0 ? 1 : 0) statisticTable := table.new(position.bottom_right, columns = statisticGroupSize + 2, rows = statisticTableSteps + 1, border_width = 1) // render headers for i = 0 to (statisticGroupSize - 1) statisticHeaderContent = str.tostring(i + 1) table.cell(statisticTable, 1 + i, 0, statisticHeaderContent, bgcolor = statisticColorGray) // render time points for i = 0 to (statisticTableSteps - 1) statisticPointContent = str.format("{0,date,medium}", array.get(statisticPeriodTime, i * statisticGroupSize)) table.cell(statisticTable, 0, 1 + i, statisticPointContent, bgcolor = statisticColorGray) // render the result statisticResultCummulative = 0.0 for i = 0 to (array.size(statisticPeriodTime) - 1) statisticColumn = 1 + i % statisticGroupSize statisticRow = 1 + math.floor(i / statisticGroupSize) statisticResult = array.get(statisticPeriodResult, i) statisticResultCummulative := (i % statisticGroupSize == 0) ? 0.0 : statisticResultCummulative statisticResultCummulative := (1 + statisticResultCummulative) * (1 + statisticResult) - 1 statisticResultColor = statisticResult > 0 ? statisticColorGreen : statisticColorRed table.cell(statisticTable, statisticColumn, statisticRow, str.tostring(math.round(statisticResult * 100, statisticPrecision)), bgcolor = statisticResultColor) // if it is the last item of the row or data array isStatisticLastOfTheRow = ((i + 1) % statisticGroupSize) == 0 isStatisticLastOfTheData = i == (statisticLength - 1) if (isStatisticLastOfTheRow or isStatisticLastOfTheData) resultsTableCummulativeCellColor = statisticResultCummulative > 0 ? statisticColorGreen : statisticColorRed resultsTableCummulativeCellContent = str.tostring(math.round(statisticResultCummulative * 100, statisticPrecision)) table.cell(statisticTable, 1 + statisticGroupSize, statisticRow, resultsTableCummulativeCellContent, bgcolor = resultsTableCummulativeCellColor)