Mysql
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Mysql

Cách gửi các truy vấn mysql động của C ++ và mysql

Sử dụng một câu lệnh đã chuẩn bị sẵn, cho phép bạn tham số hóa các giá trị, tương tự như cách các hàm cho phép bạn tham số hóa các biến trong khối câu lệnh. Nếu sử dụng MySQL Connector / C ++ :

// use std::unique_ptr, boost::shared_ptr, or whatever is most appropriate for RAII
// Connector/C++ requires boost, so 
std::unique_ptr<sql::Connection> db;
std::unique_ptr<sql::PreparedStatement> getPassword
std::unique_ptr<sql::ResultSet> result;
std::string name = "Nikolai Gogol";
std::string password;

...

getPassword = db->prepareStatement("SELECT pass FROM users WHERE name=? LIMIT 1");

getPassword->setString(1, name);
result = getPassword->execute();
if (result->first()) {
    password = result->getString("pass");
} else {
    // no result
    ...
}

// smart pointers will handle deleting the sql::* instances

Tạo các lớp để xử lý quyền truy cập cơ sở dữ liệu và gói nó trong một phương thức và phần còn lại của ứng dụng thậm chí không cần biết rằng cơ sở dữ liệu đang được sử dụng.

Nếu bạn thực sự muốn sử dụng API C cũ vì một số lý do:

MYSQL *mysql;
...

const my_bool yes=1, no=0;
const char* getPassStmt = "SELECT password FROM users WHERE username=? LIMIT 1";
MYSQL_STMT *getPassword;
MYSQL_BIND getPassParams;
MYSQL_BIND result;

std::string name = "Nikolai Gogol";
std::string password;

if (! (getPassword = mysql_stmt_init(mysql))) {
    // error: couldn't allocate space for statement
    ...
}
if (mysql_stmt_prepare(getPassword, getPassStmt, strlen(getPassStmt))) {
    /* error preparing statement; handle error and 
       return early or throw an exception. RAII would make
       this easier.
    */
    ...
} else {
    unsigned long nameLength = name.size();
    memset(&getPassParams, 0, sizeof(getPassParams));
    getPassParams.buffer_type = MYSQL_TYPE_STRING;
    getPassParams.buffer = (char*) name.c_str();
    getPassParams.length = &nameLength;

    if (mysql_stmt_bind_param(getPassword, &getPassParams)) {
        /* error binding param */
        ...
    } else if (mysql_stmt_execute(getPassword)) {
        /* error executing query */
        ...
    } else {
        // for mysql_stmt_num_rows()
        mysql_stmt_store_result(getPassword);
        if (mysql_stmt_num_rows(getPassword)) {
            unsigned long passwordLength=0;
            memset(&result, 0, sizeof(result));
            result.length = &passwordLength;
            mysql_stmt_bind_result(getPassword, &result);

            mysql_stmt_fetch(getPassword);
            if (passwordLength > 0) {
                result.buffer = new char[passwordLength+1];
                memset(result.buffer, 0, passwordLength+1);
                result.buffer_length = passwordLength+1;
                if (mysql_stmt_fetch_column(getPassword, &result, 0, 0)) {
                    ...
                } else {
                    password = static_cast<const char*>(result.buffer);
                }
            }
        } else {
            // no result
            cerr << "No user '" << name << "' found." << endl;
        }
    }
    mysql_stmt_free_result(getPassword);
}
mysql_stmt_close(getPassword);

mysql_close(mysql);

Như bạn thấy, Connector / C ++ đơn giản hơn. Nó cũng ít bị lỗi hơn; Có lẽ tôi đã mắc nhiều lỗi khi sử dụng API C hơn là Trình kết nối / C ++.

Xem thêm:



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Hiển thị các mục nhập mà tôi có chung với một người dùng, được phân tách theo lượt thích và lượt không thích

  2. Xa HasManyThrough

  3. Điểm yếu của phương pháp xác thực người dùng này là gì?

  4. Khi nào để KHÓA BẢNG trong MySQL (bảng MyISAM)?

  5. Hợp nhất các điểm dài / vĩ độ trong một hộp giới hạn tùy thuộc vào bán kính trong MySQL