C++ là một ngôn ngữ lập trình rất khó. Phần khó nhất là học sâu, nhưng nếu bạn chỉ viết logic chiến lược bằng C++, nó sẽ không cần nhiều kiến thức sâu, miễn là nó không phải là một chiến lược rất phức tạp. Học một số điều cơ bản sẽ đủ.
Đối với một số người sử dụng C ++ không có nghĩa là nó phù hợp cho tất cả mọi người sử dụng nó. lý do là, ngôn ngữ lập trình chỉ là một công cụ. Trong giao dịch định lượng, C ++ không phải là
Nhưng trong số các tổ chức đầu tư định lượng, hầu hết phần mềm hệ thống giao dịch định lượng cơ bản được viết bằng C ++, bởi vì đặc tính ngôn ngữ độc đáo của nó làm cho nó hiệu quả và nhanh hơn các ngôn ngữ khác trong một số khía cạnh, đặc biệt là trong tính toán số. Điều này cũng có nghĩa là C ++ phù hợp hơn cho các công cụ phái sinh tài chính và giao dịch tần số cao. Vì vậy, nếu bạn muốn sử dụng một ngôn ngữ lập trình nhanh hơn, nó phải là ngôn ngữ C ++.
Để giúp mọi người hiểu nội dung của phần này nhanh hơn, trước khi giới thiệu ngôn ngữ C ++, hãy xem xét chiến lược được viết bởi C ++, để bạn có một sự hiểu biết sơ bộ về khái niệm danh từ trong phần này.
Chúng ta đều biết rằng MACD có hai đường cong, cụ thể là đường nhanh và đường chậm, hãy thiết kế một logic giao dịch dựa trên hai đường này. Khi đường nhanh vượt qua đường chậm, mở vị trí dài; khi đường nhanh xuống vượt qua đường chậm, mở vị trí ngắn.
Vị trí dài mở: Nếu hiện không có vị trí, và đường nhanh lớn hơn đường chậm.
Vị trí ngắn mở: Nếu hiện không có vị trí, và đường nhanh thấp hơn đường chậm.
Close Long position: Nếu hiện đang giữ long position, và đường nhanh thấp hơn đường chậm.
Close Short Position: Nếu hiện tại giữ short position, và đường nhanh lớn hơn đường chậm.
Sử dụng ngôn ngữ C ++ để viết logic chiến lược trên, sẽ giống như:
double position = 0; //Position status parameter, the default position is 0
uint64_t lastSignalTime = 0; // Last signal trigger time
bool onTick(string symbol) { // onTick function, inside the function is the strategy logic
auto ct = exchange.SetContractType(symbol); // set the trading variety
if (ct == false) { // if setting the trading variety is not successful
return false; // return false
}
auto r = exchange.GetRecords(); // get the k line array
if (!r.Valid || r.sizeO < 20) { // if get the k line array is not successful or the number of k line is less than 20
return false; // return false
}
auto signalTime = r[r.size() - 2].Time; // get the previous k line time
if (signalTime <= lastSignalTime) { // if the previous k line time is less than or equal to the last trigger signal time
return false; // return false
}
auto macd = TA.MACD(r); // calculate the MACD indicator
auto slow = macd[0][macd[0].size() - 2]; // get the previous k line MACD value
auto fast = macd[l][macd[l].size() - 2]; // get the previous k line MACD average value
string action; // define a string variable action
if (fast >= slow && position <= 0) { // if the previous k line macd value is greater than or equal to the previous k line macd average value, and there are no long position holding
action = "buy"; // assign buy to the variable action
} else if (fast <= slow && position >= 0) { // if the previous k line macd value is less than or equal to the previous k line macd average value, and there are no short position holding
action = "sell"; // assign sell to the variable action
}
if (actton.size() > 0) { // If there are orders for placing order
If (position != 0) { // If there are holding position
ext::Trade("cover", symbol); // call the C++ trading class library and close all position
}
position = ext::Trade(action, symbol, 1); // call the C++ trading class library, placing orders according the direction of variable "action", and renew the position status
lastSignalTime = signalTime; // reset the time of last trigger signal
}
return true; // return true
}
void main() { // program starts from here
while (true) { // enter the loop
if (exchange.IO("status") == 0) { // if the connection with the exchange is not successful
Sleep(1000); // pause for 1 second
continue; // skip this loop, continue to the next loop
}
if (!onTtck("this_week")) { // if the connection is ok, enter the if loop and start to execute the onTick function
Sleep(1000); // pause for 1 second
}
}
}
Mã trên là một chiến lược giao dịch định lượng hoàn chỉnh được viết bằng C ++. Nó có thể được áp dụng trong thị trường thực và sẽ tự động đặt lệnh. Về kích thước mã, nó phức tạp hơn các ngôn ngữ khác. Bởi vì ngôn ngữ C ++ chủ yếu dành cho phát triển chiến lược tần số cao trên nền tảng FMZ Quant.
Mặc dù phần mã hóa là một chút nhiều hơn trước đây, rất nhiều thư viện lớp giao dịch không cần thiết đã được giảm, và hầu hết các xử lý cấp hệ thống cơ bản được đóng gói bởi nền tảng FMZ Quant.
Đối với người mới bắt đầu, quá trình thiết kế toàn bộ chiến lược vẫn không thay đổi: thiết lập đa dạng thị trường, thu thập dữ liệu đường K, thu thập thông tin vị trí, tính toán logic giao dịch và đặt lệnh.
Các biến và tên hàm trong C++ là nhạy với chữ cái lớn, có nghĩa là thử tên biến và thử tên biến là hai biến khác nhau. ký tự đầu tiên của bộ nhận dạng phải là một chữ cái, một dấu gạch dưới
mohd zara abc move_name a_123
myname50 _temp j a23b9 retVal
Các bình luận bao gồm các bình luận một dòng và bình luận cấp khối. Các bình luận một dòng bắt đầu với hai dấu gạch ngạch, bắt đầu với dấu gạch ngạch và dấu ngoặc ( /* ), kết thúc với dấu ngoặc và dấu ngoặc ( */ ), như được hiển thị dưới đây:
// this is a single-line comment
/*
* this is a multiple-line comment
* block-level comments
*
*/
Trong C++, dấu chấm là dấu chấm kết thúc câu lệnh. nghĩa là, mỗi câu lệnh phải kết thúc bằng dấu chấm kết thúc. Nó chỉ ra kết thúc của một thực thể logic. Ví dụ, đây là ba câu lệnh khác nhau:
x = y;
y = y + 1;
add(x, y);
Một biến là một khu vực lưu trữ hoạt động. Để xác định một biến trong C ++, trước tiên bạn phải xác định loại biến. Trong việc phát triển các chiến lược giao dịch định lượng, chúng tôi thường sử dụng các loại là: số nguyên (int ), phơi lội (double ), chuỗi (dòng chuỗi) và loại dẫn xuất tự động (tự động).
Số nguyên có thể được hiểu là các số nguyên; các loại dấu phẩy nổi có thể được hiểu là các số có dấu thập phân; chuỗi là chữ cái, có thể là các ký tự tiếng Anh hoặc ngôn ngữ khác.
Đôi khi khi chúng ta gọi một API, nhưng chúng ta không biết liệu API này sẽ cho chúng ta loại dữ liệu nào để trả về, vì vậy sử dụng loại dẫn xuất tự động (auto ) sẽ giúp chúng ta tự động xác định loại dữ liệu.
int numbers = 10; // use int to define a integer variable and assign 10 to this variable
double PI = 3.14159; // use double to define a float variable and assign 10 to this variable
string name = "FMZ Quant"; // use string to define a string variable and assign "FMZ Quant" to this variable
auto bar = exchange.GetRecords(); // use auto to define a variable (automatic derivation type) and assign k line array to this variable
Một mảng là một container để lưu trữ dữ liệu. Một mảng C++ có thể lưu trữ một tập hợp thứ tự cố định của các yếu tố cùng loại với kích thước cố định. Vì vậy, trong C++, để tuyên bố một mảng, bạn cần phải chỉ định loại yếu tố và số lượng các yếu tố. Tất cả các mảng đều có chỉ số 0 như yếu tố đầu tiên của chúng. Để có được dữ liệu đầu tiên trong mảng là " [0] ", dữ liệu thứ hai là " [1] ", v.v., như sau:
// define a array, array name is balance. there are 5 floating(double) type data inside it
double balance[5] = {1000.0, 2.0, 3.4, 7.0, 50.0};
double salary = balance[0]; // get the first data in the array, the result is : 1000.0
double salary = balance[1]; // get the second data in the array, the result is : 2.0
Một hàm là một tập các lệnh thực hiện một nhiệm vụ cùng nhau. Việc khai báo một hàm bao gồm: tên của hàm, loại trả về và các tham số. Loại trả về là kiểu dữ liệu được trả về khi hàm được chạy khi tôi gọi hàm này; tham số là tùy chọn, và hàm cũng không thể chứa các tham số. Khi hàm được gọi, bạn cũng có thể truyền một tham số cho hàm. Hãy xem ví dụ sau:
// create a function called "max"
// when this function is called, it returns the int type data
// this function has 2 parameters, and they both are int type
// this function is for passing 2 int type numbers, and return the bigger one
int max(int num1, int num2) {
int result; // define a int variable result
if (num1 > num2) // if the num1 > num2
result = num1; // assign the value of num1 to result
else // otherwise
result = num2; // assign the value of num2 to result
return result; // return the value of result
}
Sử dụng C ++ để viết các chiến lược giao dịch định lượng, có ba toán tử thường được sử dụng: toán tử số học, toán tử quan hệ, toán tử logic và toán tử phân bổ. Các toán tử số học là các hoạt động toán học của việc cộng, trừ, nhân và chia. Các toán tử quan hệ có thể so sánh xem hai giá trị nhỏ hơn hay lớn hơn. Các toán tử logic chủ yếu bao gồm: logic AND, logic OR và logic non. Các toán tử phân bổ là việc phân bổ biến mà chúng ta đã nói về trước đây. Như được hiển thị dưới đây:
int main() {
// arithmetic operator
int a = 10;
int b = 5;
a + b; // the result is 15
a - b; // the result is 5
a * b; // the result is 50
a / b; // the result is 2
a % b; // the result is 0
a++; // the result is 11
a--; // the result is 9
// relational operators
a == b; // the result is false
a != b; // the result is true
a >= b; // the result is true
a <= b; // the result is false
logical operators
true && true // the result is true
true && false // the result is false
false || false // the result is false
true || false // the result is true
!(true) // the result is false
!(false) // the result is true
return 0;
}
Nếu có một biểu thức 100*(10-1)/(10+5), bước nào được chương trình tính toán đầu tiên? Toán học trung học cho chúng ta biết: Nếu nó là cùng một mức độ hoạt động, nó thường được tính toán từ trái sang phải; Nếu có phép cộng và trừ, và nhân và chia, trước tiên tính toán phép nhân và chia, sau đó thêm và trừ; Nếu có ngoặc, đầu tiên tính toán bên trong ngoặc; Nếu luật hoạt động được đáp ứng, luật tính toán có thể được sử dụng cho phép tính. nguyên tắc trên cùng cho C ++, như được hiển thị bên dưới:
auto num = 100*(10-1)/(10+5); // the value of num is 60
1 > 2 && (2 > 3 || 3 < 5); // the result is : false
1 > 2 && 2 > 3 || 3 < 5; // the result is : true
Thông thường khi viết mã, chúng ta luôn cần thực hiện các hành động khác nhau cho các quyết định khác nhau. chúng ta có thể sử dụng các câu lệnh có điều kiện trong mã của chúng ta để hoàn thành nhiệm vụ này. Trong C ++, chúng ta có thể sử dụng các câu lệnh có điều kiện sau:
If statement - Sử dụng lệnh này để thực thi mã chỉ khi điều kiện được chỉ định là đúng
If...else statement - execute code if the specified condition is true, the other code executed when the condition is false Nếu... nếu câu lệnh - execute code nếu điều kiện được chỉ định là true, code khác được thực thi khi điều kiện là false
If...else if...else statement - sử dụng lệnh này để chọn một trong nhiều khối mã để thực thi
Tuyên bố chuyển đổi - Sử dụng lệnh này để chọn một trong nhiều khối mã để thực thi
Câu lệnh này chỉ thực thi mã nếu điều kiện được chỉ định là đúng. Vui lòng sử dụng chữ cái nhỏ if. Sử dụng chữ cái lớn (IF) sẽ tạo ra một lỗi C++! Như được hiển thị dưới đây:
// grammar
if (condition) {
//execute code only if the condition is true
}
//example
if (time<20) { // if current time is less than 20:00
x = "Good day"; // when the time is less that 20:00, assign the "good day" to x
}
mã thực thi nếu điều kiện được chỉ định là đúng, mã khác được thực thi khi điều kiện là sai, như được hiển thị dưới đây:
//grammar
if (condition) {
// execute code if the condition is true
} else {
// the other code executed when the condition is false
}
//example
if (time<20) { // if current time is less than 20:00
x = "Good day"; // when the time is less that 20:00, assign the "good day" to x
} else { // otherwise
x = "Good evening"; // assign the "Good evening" to x
}
Sử dụng lệnh này để chọn một trong nhiều khối mã để thực thi
switch (condition)
{
case 1: // code to be executed if condition = 1;
break;
case 2: // code to be executed if condition = 2;
break;
default: // code to be executed if condition doesn't match any cases
}
Chuỗi For có thể thực hiện N lần các khối mã lặp đi lặp lại và luồng thực thi của nó như thế này (như được hiển thị bên dưới):
for (int a = 10; a < 20; a++){
// code block
}
Bước 1: Thực thi int a = 0 và chỉ thực thi một lần. Mục đích của nó là để tuyên bố một biến số nguyên và khởi tạo nó thành 0 để điều khiển vòng lặp for.
Bước 2: Thực hiện a<20. Nếu đúng, thực hiện khối mã của dòng 2.
Bước 3: Thực hiện a ++, sau khi thực hiện a ++, a trở thành 11.
Bước 4: Thực hiện a<20 một lần nữa, và các bước thứ hai, thứ ba và thứ tư sẽ được thực hiện nhiều lần. Cho đến khi a<20 là sai, nếu sai, khối mã của dòng 2 sẽ không được thực hiện, và toàn bộ vòng lặp for đã hoàn thành.
Chúng ta đều biết rằng thị trường luôn thay đổi. Nếu bạn muốn có được mảng K-line mới nhất, bạn phải liên tục chạy cùng một mã lặp đi lặp lại. Sau đó sử dụng vòng lặp while là lựa chọn tốt nhất. Miễn là điều kiện được chỉ định là đúng, vòng lặp sẽ tiếp tục nhận được dữ liệu mảng k-line mới nhất.
void main() {
auto ct = exchange.SetContractType(symbol); //set the trading variety
while(true) {
auto r = exchange.GetRecords(); // constantly getting k-line arrays
}
}
Loop có các điều kiện tiên quyết. Chỉ khi điều kiện tiên quyết này là "true", vòng lặp sẽ bắt đầu làm một cái gì đó lặp đi lặp lại, cho đến khi điều kiện tiên quyết là "false", vòng lặp sẽ kết thúc. Nhưng sử dụng câu lệnh break có thể nhảy ra khỏi vòng lặp ngay lập tức trong quá trình thực thi vòng lặp;
# including <iostream>
using namespace std;
int main() {
for(int a = 0; a < 5; a++) {
if(a == 2) break;
cout << a << endl;
}
return 0;
}
// print out : 0, 1
Các lệnh tiếp tục cũng nhảy ra khỏi vòng lặp, nhưng nó không nhảy ra khỏi toàn bộ vòng lặp. Thay vào đó, ngắt một vòng lặp và tiếp tục đến vòng lặp tiếp theo. Như được hiển thị dưới đây, khi a bằng 2, vòng lặp được ngắt, và vòng lặp tiếp theo được tiếp tục cho đến khi điều kiện tiên quyết của vòng lặp là "sai" để nhảy ra khỏi toàn bộ vòng lặp.
# including <iostream>
using namespace std;
int main() {
for(int a = 0; a < 5; a++) {
if(a == 2) continue;
cout << a << endl;
}
return 0;
}
// print out : 0, 1, 3, 4
Tuyên bố return chấm dứt việc thực hiện hàm và trả về giá trị của hàm. Tuyên bố return chỉ có thể xuất hiện trong phần thân của hàm, và bất kỳ vị trí nào khác trong mã sẽ gây ra lỗi cú pháp!
# including <iostream>
using namespace std;
int add(int num1, int num2) {
return num1 + num2; // The add function returns the sum of two parameters
}
int main()
{
cout << add(5, 10); // call the add function, and print out the result:50
return 0;
}
Trên nền tảng FMZ Quant, sẽ rất thuận tiện để viết một chiến lược bằng C ++. FMZ Quant có rất nhiều khung chiến lược tiêu chuẩn chính thức và thư viện lớp giao dịch, chẳng hạn như sau:
bool onTick() { //onTick function
// strategy logic
}
void main() { // program starts from here
while (true) { // enter the loop
if (exchange.IO("status") == 0) { // if the exchange connection is not stable
sleep(1000); // pause for 1 second
continue; // skip this loop, enter the next loop
}
if (!onTick()) { // if the exchange connection is stable, enter this if statement, start to execute the onTick function
sleep(1000);// pause for 1 second
}
}
}
Như đã được hiển thị ở trên, đây là một framework chiến lược tiêu chuẩn, và các định dạng này được cố định. Sử dụng framework để viết một chiến lược. Bạn chỉ cần viết logic chiến lược từ dòng thứ hai. Việc mua lại thị trường và xử lý lệnh khác được xử lý bởi framework và thư viện lớp giao dịch, bạn chỉ cần tập trung vào phát triển chiến lược.
Nếu bạn cần viết chiến lược phức tạp hơn, vui lòng tham khảo tài liệu API ngôn ngữ C ++ của nền tảng FMZ Quant, hoặc trực tiếp tham khảo dịch vụ khách hàng chính thức về dịch vụ viết
Chìa khóa của giao dịch định lượng là chiến lược giao dịch, không phải là các công cụ giao dịch (ngôn ngữ lập trình).