共用方式為


SQL:自訂記錄集的 SQL 語句 (ODBC)

本主題將說明:

  • 架構如何建構 SQL 語句

  • 如何覆寫 SQL 語句

注意

此資訊適用於 MFC ODBC 類別。 如果您使用 MFC DAO 類別,請參閱 DAO 說明中的主題。

SQL 語句建構

您的記錄集主要以 SQL SELECT 語句為基礎來選取記錄。 當您使用精靈宣告類別時,它會撰寫成員函式的 GetDefaultSQL 覆寫版本,看起來像這樣(針對名為 CAuthors 的記錄集類別)。

CString CAuthors::GetDefaultSQL()
{
    return "AUTHORS";
}

根據預設,此覆寫會傳回您使用精靈指定的資料表名稱。 在此範例中,資料表名稱為 「AUTHORS」。當您稍後通話記錄集 Open 的成員函式時, Open 會建構表單的最終 SELECT 語句:

SELECT rfx-field-list FROM table-name [WHERE m_strFilter]
       [ORDER BY m_strSort]

其中 table-name 是透過呼叫 GetDefaultSQL 取得,並從 rfx-field-list 中的 DoFieldExchange RFX 函式呼叫取得。 除非您在執行時間以覆寫版本取代 SELECT 語句,否則這是您取得 的,不過您也可以使用參數或篩選來修改預設語句。

注意

如果您指定包含 (或 可以包含) 空格的資料行名稱,則必須以方括弧括住名稱。 例如,名稱 「First Name」 應該是 「[First Name]」。

若要覆寫預設 SELECT 語句,請在呼叫 Open 時傳遞包含完整 SELECT 語句的字串。 記錄集會使用您提供的字串,而不是建構自己的預設字串。 如果您的取代語句包含 WHERE 子句,請勿在 中 m_strFilter 指定篩選,因為您接著會有兩個篩選語句。 同樣地,如果您的取代語句包含 ORDER BY 子句,請勿在 中 m_strSort 指定排序,這樣您就不會有兩個排序語句。

注意

如果您在篩選中使用常值字串(或 SQL 語句的其他部分),您可能必須以 DBMS 特定的常值前置詞和常值尾碼字元(或字元)括住這類字串。

視 DBMS 而定,您可能也會遇到特殊的語法需求,例如外部聯結等作業。 使用 ODBC 函式從 DBMS 的驅動程式取得此資訊。 例如,呼叫 ::SQLGetTypeInfo 特定資料類型,例如 SQL_VARCHAR ,以要求LITERAL_PREFIX和LITERAL_SUFFIX字元。 如果您要撰寫與資料庫無關的程式碼,請參閱 ODBC 程式設計人員參考 中的 附錄 C:SQL 文法 ,以取得詳細的語法資訊。

除非傳遞自訂 SQL 語句,否則記錄集物件會建構用來選取記錄的 SQL 語句。 完成此作業的方式主要取決於您傳入成員函式之 lpszSQL 參數 Open 的值。

SQL SELECT 語句的一般形式為:

SELECT [ALL | DISTINCT] column-list FROM table-list
    [WHERE search-condition][ORDER BY column-list [ASC | DESC]]

將 DISTINCT 關鍵字新增 至記錄集 SQL 語句的其中一種方式,是在 中的第一個 RFX 函式呼叫中 DoFieldExchange 內嵌 關鍵字。 例如:

...
    RFX_Text(pFX, "DISTINCT CourseID", m_strCourseID);
...

注意

請只搭配開啟為唯讀的記錄集使用這項技術。

覆寫 SQL 語句

下表顯示 lpszSQL 參數對 Open 的可能性。 資料表中的案例會在下表之後說明。

lpszSQL 參數和產生的 SQL 字串

大小寫 您傳入 lpszSQL 的內容 產生的 SELECT 語句
1 NULL SELECT rfx-field-list FROM table-name

CRecordset::Open 呼叫 GetDefaultSQL 以取得資料表名稱。 產生的字串是 2 到 5 的其中一個案例,視傳回的專案 GetDefaultSQL 而定。
2 資料表名稱 SELECT rfx-field-list FROM table-name

欄位清單取自 中的 DoFieldExchange RFX 語句。 如果 m_strFilterm_strSort 不是空的,請新增 WHERE 和/或 ORDER BY 子句。
3* 完整的 SELECT 語句,但沒有 WHERE ORDER BY 子句 傳遞時。 如果 m_strFilterm_strSort 不是空的,請新增 WHERE 和/或 ORDER BY 子句。
4* 具有 WHERE 和/或 ORDER BY 子句的完整 SELECT 語句 傳遞時。 m_strFilter 和/或 m_strSort 必須保持空白,或產生兩個篩選和/或排序語句。
5 * 預存程式的呼叫 傳遞時。

* m_nFields必須小於或等於 SELECT 語句中指定的 資料行數目。 SELECT 語句中所 指定之每個資料行的資料類型必須與對應 RFX 輸出資料行的資料類型相同。

案例 1 lpszSQL = Null

記錄集選取專案取決於通話記錄集時 CRecordset::Open 傳回的專案 GetDefaultSQL 。 案例 2 到 5 描述可能的字串。

案例 2 lpszSQL = 資料表名稱

記錄集會使用記錄欄位交換 (RFX),從記錄集類別的 覆寫 DoFieldExchange 中提供的資料行名稱建置資料行清單。 如果您使用精靈來宣告記錄集類別,則此案例的結果與案例 1 相同(前提是您傳遞精靈中指定的相同資料表名稱)。 如果您不使用精靈來撰寫類別,案例 2 是建構 SQL 語句的最簡單方式。

下列範例會建構從 MFC 資料庫應用程式選取記錄的 SQL 語句。 當架構呼叫 GetDefaultSQL 成員函式時,函式會傳回資料表 SECTION 的名稱 。

CString CEnrollSet::GetDefaultSQL()
{
    return "SECTION";
}

若要取得 SQL SELECT 語句的資料行名稱,架構會呼叫 DoFieldExchange 成員函式。

void CEnrollSet::DoFieldExchange(CFieldExchange* pFX)
{
    pFX->SetFieldType(CFieldExchange::outputColumn);
    RFX_Text(pFX, "CourseID", m_strCourseID);
    RFX_Text(pFX, "InstructorID", m_strInstructorID);
    RFX_Text(pFX, "RoomNo", m_strRoomNo);
    RFX_Text(pFX, "Schedule", m_strSchedule);
    RFX_Text(pFX, "SectionNo", m_strSectionNo);
}

完成時,SQL 語句看起來像這樣:

SELECT CourseID, InstructorID, RoomNo, Schedule, SectionNo
    FROM SECTION

案例 3 lpszSQL = SELECT/FROM 語句

您可以手動指定資料行清單,而不是依賴 RFX 自動建構它。 您可能會想要在下列情況下執行此動作:

  • 您想要在 SELECT 之後 指定 DISTINCT 關鍵字。

    您的資料行清單應該以與 中 DoFieldExchange 所列的相同順序來比對資料行名稱和類型。

  • 您有理由使用 ODBC 函數 ::SQLGetData 手動擷取資料行值,而不是依賴 RFX 為您系結和擷取資料行。

    例如,您可能想要容納應用程式在散發應用程式之後新增至資料庫資料表的新資料行。 您需要新增這些額外的欄位資料成員,這些成員在您使用精靈宣告類別時並不知道。

    您的資料行清單應該以與列出的 DoFieldExchange 資料行名稱和類型相同順序比對,後面接著手動系結資料行的名稱。 如需詳細資訊,請參閱 記錄集:動態系結資料行 (ODBC)

  • 您想要藉由在 FROM 子句中 指定多個資料表來聯結資料表。

    如需資訊和範例,請參閱 Recordset:執行聯結 (ODBC)

案例 4 lpszSQL = SELECT/FROM Plus WHERE 和/或 ORDER BY

您可以指定所有專案:資料行清單(根據 中的 DoFieldExchange RFX 呼叫)、資料表清單,以及 WHERE 和/或 ORDER BY 子句的內容 。 如果您以這種方式指定 WHERE 和/或 ORDER BY 子句,請勿使用 m_strFilter 和/或 m_strSort

案例 5 lpszSQL = 預存程序呼叫

如果您需要呼叫預先定義的查詢(例如 Microsoft SQL Server 資料庫中的預存程式),您必須在傳遞至 lpszSQL 的字串中撰寫 CALL 語句。 精靈不支援宣告記錄集類別來呼叫預先定義的查詢。 並非所有預先定義的查詢都會傳回記錄。

如果預先定義的查詢未傳回記錄,您可以直接使用 CDatabase 成員函式 ExecuteSQL 。 對於會傳回記錄的預先定義查詢,您也必須針對程式傳回的任何資料行手動寫入 RFX 呼叫 DoFieldExchange 。 RFX 呼叫的順序必須與預先定義的查詢相同,並傳回相同的類型。 如需詳細資訊,請參閱 Recordset:宣告預先定義查詢的類別 (ODBC)

另請參閱

SQL:SQL 和 C++ 資料類型 (ODBC)
SQL:製作直接的 SQL 呼叫 (ODBC)