Fungsi SQLGetData
Kesesuaian
Versi diperkenalkan: Kepatuhan Standar ODBC 1.0: ISO 92
Ringkasan
SQLGetData mengambil data untuk satu kolom dalam kumpulan hasil atau untuk satu parameter setelah SQLParamData mengembalikan SQL_PARAM_DATA_AVAILABLE. Ini dapat dipanggil beberapa kali untuk mengambil data panjang variabel di beberapa bagian.
Sintaks
SQLRETURN SQLGetData(
SQLHSTMT StatementHandle,
SQLUSMALLINT Col_or_Param_Num,
SQLSMALLINT TargetType,
SQLPOINTER TargetValuePtr,
SQLLEN BufferLength,
SQLLEN * StrLen_or_IndPtr);
Argumen
StatementHandle
[Input] Handel pernyataan.
Col_or_Param_Num
[Input] Untuk mengambil data kolom, ini adalah jumlah kolom yang akan mengembalikan data. Kolom tataan hasil diberi nomor dalam meningkatkan urutan kolom mulai dari 1. Kolom bookmark adalah kolom nomor 0; ini hanya dapat ditentukan jika marka buku diaktifkan.
Untuk mengambil data parameter, ini adalah ordinal parameter, yang dimulai dari 1.
TargetType
[Input] Pengidentifikasi jenis data C dari buffer *TargetValuePtr . Untuk daftar jenis data C yang valid dan pengidentifikasi jenis, lihat bagian Jenis Data C di Lampiran D: Jenis Data.
Jika TargetType SQL_ARD_TYPE, driver menggunakan pengidentifikasi jenis yang ditentukan di bidang SQL_DESC_CONCISE_TYPE ARD. Jika TargetType SQL_APD_TYPE, SQLGetData akan menggunakan jenis data C yang sama yang ditentukan di SQLBindParameter. Jika tidak, jenis data C yang ditentukan dalam SQLGetData mengambil alih jenis data C yang ditentukan dalam SQLBindParameter. Jika SQL_C_DEFAULT, driver memilih jenis data C default berdasarkan jenis data SQL sumber.
Anda juga dapat menentukan jenis data C yang diperluas. Untuk informasi selengkapnya, lihat Jenis Data C di ODBC.
TargetValuePtr
[Output] Arahkan ke buffer untuk mengembalikan data.
TargetValuePtr tidak boleh NULL.
BufferLength
[Input] Panjang buffer *TargetValuePtr dalam byte.
Driver menggunakan BufferLength untuk menghindari penulisan melewati akhir buffer *TargetValuePtr saat mengembalikan data panjang variabel, seperti karakter atau data biner. Perhatikan bahwa driver menghitung karakter penghentian null saat mengembalikan data karakter ke *TargetValuePtr. *Oleh karena itu, TargetValuePtr harus berisi ruang untuk karakter penghentian null, atau driver akan memotong data.
Ketika driver mengembalikan data panjang tetap, seperti bilangan bulat atau struktur tanggal, driver mengabaikan BufferLength dan mengasumsikan buffer cukup besar untuk menyimpan data. Oleh karena itu penting bagi aplikasi untuk mengalokasikan buffer yang cukup besar untuk data panjang tetap atau driver akan menulis melewati akhir buffer.
SQLGetData mengembalikan SQLSTATE HY090 (String tidak valid atau panjang buffer) saat BufferLength kurang dari 0 tetapi tidak ketika BufferLength adalah 0.
StrLen_or_IndPtr
[Output] Penunjuk ke buffer untuk mengembalikan panjang atau nilai indikator. Jika ini adalah pointer null, tidak ada panjang atau nilai indikator yang dikembalikan. Ini mengembalikan kesalahan ketika data yang diambil adalah NULL.
SQLGetData dapat mengembalikan nilai berikut dalam buffer panjang/indikator:
Panjang data yang tersedia untuk dikembalikan
SQL_NO_TOTAL
SQL_NULL_DATA
Untuk informasi selengkapnya, lihat Menggunakan Nilai Panjang/Indikator dan "Komentar" dalam topik ini.
Mengembalikan
SQL_SUCCESS, SQL_SUCCESS_WITH_INFO, SQL_NO_DATA, SQL_STILL_EXECUTING, SQL_ERROR, atau SQL_INVALID_HANDLE.
Diagnostik
Saat SQLGetData mengembalikan SQL_ERROR atau SQL_SUCCESS_WITH_INFO, nilai SQLSTATE terkait dapat diperoleh dengan memanggil SQLGetDiagRec dengan HandleType SQL_HANDLE_STMT dan Handle of StatementHandle. Tabel berikut mencantumkan nilai SQLSTATE yang umumnya dikembalikan oleh SQLGetData dan menjelaskan masing-masing dalam konteks fungsi ini; notasi "(DM)" mendahului deskripsi SQLSTATEs yang dikembalikan oleh Driver Manager. Kode pengembalian yang terkait dengan setiap nilai SQLSTATE SQL_ERROR, kecuali disebutkan sebaliknya.
SQLSTATE | Kesalahan | Deskripsi |
---|---|---|
01000 | Peringatan umum | Pesan informasi khusus driver. (Fungsi mengembalikan SQL_SUCCESS_WITH_INFO.) |
01004 | Data string, terpotong kanan | Tidak semua data untuk kolom yang ditentukan, Col_or_Param_Num, dapat diambil dalam satu panggilan ke fungsi. SQL_NO_TOTAL atau panjang data yang tersisa di kolom yang ditentukan sebelum panggilan saat ini ke SQLGetData dikembalikan dalam *StrLen_or_IndPtr. (Fungsi mengembalikan SQL_SUCCESS_WITH_INFO.) Untuk informasi selengkapnya tentang menggunakan beberapa panggilan ke SQLGetData untuk satu kolom, lihat "Komentar." |
01S07 | Pemotongan pecahan | Data yang dikembalikan untuk satu atau beberapa kolom dipotong. Untuk jenis data numerik, bagian pecahan dari angka dipotong. Untuk jenis data waktu, tanda waktu, dan interval yang berisi komponen waktu, bagian pecahan waktu dipotong. (Fungsi mengembalikan SQL_SUCCESS_WITH_INFO.) |
07006 | Pelanggaran atribut jenis data terbatas | Nilai data kolom dalam tataan hasil tidak dapat dikonversi ke tipe data C yang ditentukan oleh argumen TargetType. |
07009 | Indeks deskriptor tidak valid | Nilai yang ditentukan untuk argumen Col_or_Param_Num adalah 0, dan atribut pernyataan SQL_ATTR_USE_BOOKMARKS diatur ke SQL_UB_OFF. Nilai yang ditentukan untuk argumen Col_or_Param_Num lebih besar dari jumlah kolom dalam tataan hasil. Nilai Col_or_Param_Num tidak sama dengan ordinal parameter yang tersedia. (DM) Kolom yang ditentukan terikat. Deskripsi ini tidak berlaku untuk driver yang mengembalikan bitmask SQL_GD_BOUND untuk opsi SQL_GETDATA_EXTENSIONS di SQLGetInfo. (DM) Jumlah kolom yang ditentukan kurang dari atau sama dengan jumlah kolom terikat tertinggi. Deskripsi ini tidak berlaku untuk driver yang mengembalikan bitmask SQL_GD_ANY_COLUMN untuk opsi SQL_GETDATA_EXTENSIONS di SQLGetInfo. (DM) Aplikasi telah memanggil SQLGetData untuk baris saat ini; jumlah kolom yang ditentukan dalam panggilan saat ini kurang dari jumlah kolom yang ditentukan dalam panggilan sebelumnya; dan driver tidak mengembalikan bitmask SQL_GD_ANY_ORDER untuk opsi SQL_GETDATA_EXTENSIONS di SQLGetInfo. (DM) Argumen TargetType SQL_ARD_TYPE, dan catatan deskriptor Col_or_Param_Num di ARD gagal dalam pemeriksaan konsistensi. (DM) Argumen TargetType SQL_ARD_TYPE, dan nilai di bidang SQL_DESC_COUNT ARD kurang dari argumen Col_or_Param_Num . |
08S01 | Kegagalan tautan komunikasi | Tautan komunikasi antara driver dan sumber data tempat driver tersambung gagal sebelum fungsi selesai diproses. |
22002 | Variabel indikator diperlukan tetapi tidak disediakan | StrLen_or_IndPtr adalah penunjuk null dan data NULL diambil. |
22003 | Nilai numerik di luar rentang | Mengembalikan nilai numerik (sebagai numerik atau string) untuk kolom akan menyebabkan seluruh (dibandingkan dengan pecahan) bagian dari angka yang akan dipotong. Untuk informasi selengkapnya, lihat Lampiran D: Jenis Data. |
22007 | Format tanggalwaktu tidak valid | Kolom karakter dalam tataan hasil terikat ke struktur tanggal, waktu, atau tanda waktu C, dan nilai dalam kolom masing-masing adalah tanggal, waktu, atau tanda waktu yang tidak valid. Untuk informasi selengkapnya, lihat Lampiran D: Jenis Data. |
22012 | Pembagian dengan nol | Nilai dari ekspresi aritmatika yang menghasilkan pembagian dengan nol dikembalikan. |
22015 | Meluapnya bidang interval | Menetapkan dari jenis SQL numerik atau interval yang tepat ke jenis C interval menyebabkan hilangnya digit signifikan di bidang utama. Saat mengembalikan data ke tipe C interval, tidak ada representasi nilai jenis SQL dalam jenis C interval. |
22018 | Nilai karakter tidak valid untuk spesifikasi cast | Kolom karakter dalam tataan hasil dikembalikan ke buffer karakter C, dan kolom berisi karakter yang tidak ada representasi dalam kumpulan karakter buffer. Jenis C adalah jenis data numerik, tanggalwaktu, atau interval yang tepat atau perkiraan; jenis SQL kolom adalah jenis data karakter; dan nilai dalam kolom bukan harfiah yang valid dari jenis C terikat. |
24000 | Status kursor tidak valid | (DM) Fungsi ini dipanggil tanpa terlebih dahulu memanggil SQLFetch atau SQLFetchScroll untuk memosisikan kursor pada baris data yang diperlukan. (DM) StatementHandle berada dalam status dijalankan, tetapi tidak ada kumpulan hasil yang terkait dengan StatementHandle. Kursor terbuka pada StatementHandle dan SQLFetch atau SQLFetchScroll telah dipanggil, tetapi kursor diposisikan sebelum awal kumpulan hasil atau setelah akhir tataan hasil. |
HY000 | Kesalahan umum | Terjadi kesalahan yang tidak ada SQLSTATE tertentu dan tidak ada SQLSTATE khusus implementasi yang ditentukan. Pesan kesalahan yang dikembalikan oleh SQLGetDiagRec di buffer MessageText menjelaskan kesalahan dan penyebabnya. |
HY001 | Kesalahan alokasi memori | Driver tidak dapat mengalokasikan memori yang diperlukan untuk mendukung eksekusi atau penyelesaian fungsi. |
HY003 | Jenis program di luar rentang | (DM) Argumen TargetType bukan tipe data yang valid, SQL_C_DEFAULT, SQL_ARD_TYPE (dalam kasus pengambilan data kolom), atau SQL_APD_TYPE (jika mengambil data parameter). (DM) Argumen Col_or_Param_Num adalah 0, dan argumen TargetType tidak SQL_C_BOOKMARK untuk bookmark panjang tetap atau SQL_C_VARBOOKMARK untuk bookmark panjang variabel. |
HY008 | Operasi dibatalkan | Pemrosesan asinkron diaktifkan untuk StatementHandle. Fungsi ini dipanggil, dan sebelum selesai dieksekusi, SQLCancel atau SQLCancelHandle dipanggil pada StatementHandle, dan kemudian fungsi dipanggil lagi pada StatementHandle. Fungsi ini dipanggil, dan sebelum selesai dieksekusi, SQLCancel atau SQLCancelHandle dipanggil pada StatementHandle dari utas yang berbeda dalam aplikasi multithread, dan kemudian fungsi dipanggil lagi pada StatementHandle. |
HY009 | Penggunaan pointer null tidak valid | (DM) Argumen TargetValuePtr adalah penunjuk null. |
HY010 | Kesalahan urutan fungsi | (DM) StatementHandle yang ditentukan tidak dalam status dijalankan. Fungsi ini dipanggil tanpa terlebih dahulu memanggil fungsi SQLExecDirect, SQLExecute , atau katalog. (DM) Fungsi eksekusi asinkron dipanggil untuk handel koneksi yang terkait dengan StatementHandle. Fungsi asinkron ini masih dijalankan ketika fungsi SQLGetData dipanggil. (DM) Fungsi eksekusi asinkron (bukan yang ini) dipanggil untuk StatementHandle dan masih dijalankan ketika fungsi ini dipanggil. (DM) SQLExecute, SQLExecDirect, SQLBulkOperations, atau SQLSetPos dipanggil untuk StatementHandle dan dikembalikan SQL_NEED_DATA. Fungsi ini dipanggil sebelum data dikirim untuk semua parameter atau kolom data-at-execution. (DM) StatementHandle berada dalam status dijalankan, tetapi tidak ada kumpulan hasil yang terkait dengan StatementHandle. Panggilan ke SQLExeceute, SQLExecDirect, atau SQLMoreResults mengembalikan SQL_PARAM_DATA_AVAILABLE, tetapi SQLGetData dipanggil, bukan SQLParamData. |
HY013 | Kesalahan manajemen memori | Panggilan fungsi tidak dapat diproses karena objek memori yang mendasar tidak dapat diakses, mungkin karena kondisi memori yang rendah. |
HY090 | String atau panjang buffer tidak valid | (DM) Nilai yang ditentukan untuk argumen BufferLength kurang dari 0. Nilai yang ditentukan untuk argumen BufferLength kurang dari 4, argumen Col_or_Param_Num diatur ke 0, dan driver adalah driver ODBC 2*.x*. |
HY109 | Posisi kursor tidak valid | Kursor diposisikan (oleh SQLSetPos, SQLFetch, SQLFetchScroll, atau SQLBulkOperations) pada baris yang telah dihapus atau tidak dapat diambil. Kursor adalah kursor khusus maju, dan ukuran set baris lebih besar dari satu kursor. |
HY117 | Koneksi ditangguhkan karena status transaksi yang tidak diketahui. Hanya fungsi putuskan sambungan dan baca-saja yang diizinkan. | (DM) Untuk informasi selengkapnya tentang status ditangguhkan, lihat Fungsi SQLEndTran. |
HYC00 | Fitur opsional tidak diimplementasikan | Driver atau sumber data tidak mendukung penggunaan SQLGetData dengan beberapa baris di SQLFetchScroll. Deskripsi ini tidak berlaku untuk driver yang mengembalikan bitmask SQL_GD_BLOCK untuk opsi SQL_GETDATA_EXTENSIONS di SQLGetInfo. Driver atau sumber data tidak mendukung konversi yang ditentukan oleh kombinasi argumen TargetType dan jenis data SQL kolom terkait. Kesalahan ini hanya berlaku ketika jenis data SQL kolom dipetakan ke jenis data SQL khusus driver. Driver hanya mendukung ODBC 2*.x*, dan argumen TargetType adalah salah satu dari berikut ini: SQL_C_NUMERIC SQL_C_SBIGINT SQL_C_UBIGINT dan salah satu jenis data C interval yang tercantum dalam Jenis Data C di Lampiran D: Jenis Data. Driver hanya mendukung versi ODBC sebelum 3.50, dan argumen TargetType SQL_C_GUID. |
HYT01 | Kesalahan waktu habis koneksi kedaluwarsa | Periode batas waktu koneksi kedaluwarsa sebelum sumber data merespons permintaan. Periode batas waktu koneksi diatur melalui SQLSetConnectAttr, SQL_ATTR_CONNECTION_TIMEOUT. |
IM001 | Driver tidak mendukung fungsi ini | (DM) Driver yang sesuai dengan StatementHandle tidak mendukung fungsi. |
IM017 | Polling dinonaktifkan dalam mode pemberitahuan asinkron | Setiap kali model pemberitahuan digunakan, polling dinonaktifkan. |
IM018 | SQLCompleteAsync belum dipanggil untuk menyelesaikan operasi asinkron sebelumnya pada handel ini. | Jika panggilan fungsi sebelumnya pada handel mengembalikan SQL_STILL_EXECUTING dan jika mode pemberitahuan diaktifkan, SQLCompleteAsync harus dipanggil pada handel untuk melakukan pasca-pemrosesan dan menyelesaikan operasi. |
Komentar
SQLGetData mengembalikan data dalam kolom tertentu. SQLGetData hanya dapat dipanggil setelah satu atau beberapa baris diambil dari hasil yang ditetapkan oleh SQLFetch, SQLFetchScroll, atau SQLExtendedFetch. Jika data panjang variabel terlalu besar untuk dikembalikan dalam satu panggilan ke SQLGetData (karena batasan dalam aplikasi), SQLGetData dapat mengambilnya di beberapa bagian. Dimungkinkan untuk mengikat beberapa kolom berturut-turut dan memanggil SQLGetData untuk yang lain, meskipun ini tunduk pada beberapa batasan. Untuk informasi selengkapnya, lihat Mendapatkan Data Panjang.
Untuk informasi tentang menggunakan SQLGetData dengan parameter output yang dialirkan, lihat Mengambil Parameter Output Menggunakan SQLGetData.
Menggunakan SQLGetData
Jika driver tidak mendukung ekstensi ke SQLGetData, fungsi hanya dapat mengembalikan data untuk kolom yang tidak terikat dengan angka yang lebih besar dari kolom terikat terakhir. Selain itu, dalam baris data, nilai argumen Col_or_Param_Num di setiap panggilan ke SQLGetData harus lebih besar dari atau sama dengan nilai Col_or_Param_Num dalam panggilan sebelumnya; yaitu, data harus diambil dalam meningkatkan urutan nomor kolom. Terakhir, jika tidak ada ekstensi yang didukung, SQLGetData tidak dapat dipanggil jika ukuran set baris lebih besar dari 1.
Driver dapat melonggarkan salah satu pembatasan ini. Untuk menentukan pembatasan apa yang dilonggarkan driver, aplikasi memanggil SQLGetInfo dengan salah satu opsi SQL_GETDATA_EXTENSIONS berikut:
SQL_GD_OUTPUT_PARAMS = SQLGetData dapat dipanggil untuk mengembalikan nilai parameter output. Untuk informasi selengkapnya, lihat Mengambil Parameter Output Menggunakan SQLGetData.
SQL_GD_ANY_COLUMN. Jika opsi ini dikembalikan, SQLGetData dapat dipanggil untuk kolom yang tidak terikat, termasuk yang sebelum kolom terikat terakhir.
SQL_GD_ANY_ORDER. Jika opsi ini dikembalikan, SQLGetData dapat dipanggil untuk kolom yang tidak terikat dalam urutan apa pun.
SQL_GD_BLOCK. Jika opsi ini dikembalikan oleh SQLGetInfo untuk SQL_GETDATA_EXTENSIONS InfoType, driver mendukung panggilan ke SQLGetData ketika ukuran set baris lebih besar dari 1 dan aplikasi dapat memanggil SQLSetPos dengan opsi SQL_POSITION untuk memosisikan kursor pada baris yang benar sebelum memanggil SQLGetData.
SQL_GD_BOUND. Jika opsi ini dikembalikan, SQLGetData dapat dipanggil untuk kolom terikat serta kolom yang tidak terikat.
Ada dua pengecualian untuk pembatasan ini dan kemampuan pengemudi untuk melonggarkannya. Pertama, SQLGetData tidak boleh dipanggil untuk kursor hanya-terusan ketika ukuran set baris lebih besar dari 1. Kedua, jika driver mendukung marka buku, driver harus selalu mendukung kemampuan untuk memanggil SQLGetData untuk kolom 0, bahkan jika tidak memungkinkan aplikasi untuk memanggil SQLGetData untuk kolom lain sebelum kolom terikat terakhir. (Ketika aplikasi bekerja dengan driver ODBC 2*.x*, SQLGetData akan berhasil mengembalikan bookmark saat dipanggil dengan Col_or_Param_Num sama dengan 0 setelah panggilan ke SQLFetch, karena SQLFetch dipetakan oleh Manajer Driver ODBC 3*.x* ke SQLExtendedFetch dengan FetchOrientation SQL_FETCH_NEXT, dan SQLGetData dengan Col_or_Param_Num 0 dipetakan oleh Manajer Driver ODBC 3*.x* ke SQLGetStmtOption dengan fOpsi SQL_GET_BOOKMARK.)
SQLGetData tidak dapat digunakan untuk mengambil marka buku untuk baris yang baru saja disisipkan dengan memanggil SQLBulkOperations dengan opsi SQL_ADD, karena kursor tidak diposisikan pada baris. Aplikasi dapat mengambil marka buku untuk baris tersebut dengan mengikat kolom 0 sebelum memanggil SQLBulkOperations dengan SQL_ADD, dalam hal ini SQLBulkOperations mengembalikan bookmark di buffer terikat. SQLFetchScroll kemudian dapat dipanggil dengan SQL_FETCH_BOOKMARK untuk memposisikan ulang kursor pada baris tersebut.
Jika argumen TargetType adalah jenis data interval, presisi terdepan interval default (2) dan presisi detik interval default (6), sebagaimana diatur dalam bidang SQL_DESC_DATETIME_INTERVAL_PRECISION dan SQL_DESC_PRECISION ARD, masing-masing digunakan untuk data. Jika argumen TargetType adalah jenis data SQL_C_NUMERIC, presisi default (ditentukan driver) dan skala default (0), seperti yang diatur dalam bidang SQL_DESC_PRECISION dan SQL_DESC_SCALE ARD, digunakan untuk data. Jika ada presisi atau skala default yang tidak sesuai, aplikasi harus secara eksplisit mengatur bidang deskriptor yang sesuai dengan panggilan ke SQLSetDescField atau SQLSetDescRec. Ini dapat mengatur bidang SQL_DESC_CONCISE_TYPE ke SQL_C_NUMERIC dan memanggil SQLGetData dengan argumen TargetType SQL_ARD_TYPE, yang akan menyebabkan nilai presisi dan skala di bidang deskriptor digunakan.
Catatan
Di ODBC 2*.x*, aplikasi mengatur TargetType ke SQL_C_DATE, SQL_C_TIME, atau SQL_C_TIMESTAMP untuk menunjukkan bahwa *TargetValuePtr adalah struktur tanggal, waktu, atau tanda waktu. Di ODBC 3*.x*, aplikasi mengatur TargetType ke SQL_C_TYPE_DATE, SQL_C_TYPE_TIME, atau SQL_C_TYPE_TIMESTAMP. Driver Manager membuat pemetaan yang sesuai jika perlu, berdasarkan aplikasi dan versi driver.
Mengambil Data Panjang Variabel di Bagian
SQLGetData dapat digunakan untuk mengambil data dari kolom yang berisi data panjang variabel di bagian - yaitu, ketika pengidentifikasi jenis data SQL kolom SQL_CHAR, SQL_VARCHAR, SQL_LONGVARCHAR, SQL_WCHAR, SQL_WVARCHAR, SQL_WLONGVARCHAR, SQL_BINARY, SQL_VARBINARY, SQL_LONGVARBINARY, atau pengidentifikasi khusus driver untuk jenis panjang variabel.
Untuk mengambil data dari kolom dalam beberapa bagian, aplikasi memanggil SQLGetData beberapa kali berturut-turut untuk kolom yang sama. Pada setiap panggilan, SQLGetData mengembalikan bagian data berikutnya. Terserah aplikasi untuk menyusun kembali bagian-bagian, berhati-hatilah untuk menghapus karakter penghentian null dari bagian perantara data karakter. Jika ada lebih banyak data untuk dikembalikan atau tidak cukup buffer dialokasikan untuk karakter yang mengakhiri, SQLGetData mengembalikan SQL_SUCCESS_WITH_INFO dan SQLSTATE 01004 (Data terpotong). Saat mengembalikan bagian terakhir data, SQLGetData mengembalikan SQL_SUCCESS. Baik SQL_NO_TOTAL maupun nol tidak dapat dikembalikan pada panggilan terakhir yang valid untuk mengambil data dari kolom, karena aplikasi kemudian tidak akan tahu berapa banyak data dalam buffer aplikasi yang valid. Jika SQLGetData dipanggil setelah ini, SQLGetData akan mengembalikan SQL_NO_DATA. Untuk informasi selengkapnya, lihat bagian berikutnya, "Mengambil Data dengan SQLGetData."
Bookmark panjang variabel dapat dikembalikan dalam bagian oleh SQLGetData. Seperti data lain, panggilan ke SQLGetData untuk mengembalikan marka buku panjang variabel di bagian akan mengembalikan SQLSTATE 01004 (Data string, terpotong kanan) dan SQL_SUCCESS_WITH_INFO ketika ada lebih banyak data yang akan dikembalikan. Ini berbeda dari kasus ketika bookmark panjang variabel dipotong oleh panggilan ke SQLFetch atau SQLFetchScroll, yang mengembalikan SQL_ERROR dan SQLSTATE 22001 (Data string, terpotong kanan).
SQLGetData tidak dapat digunakan untuk mengembalikan data panjang tetap dalam beberapa bagian. Jika SQLGetData dipanggil lebih dari satu kali berturut-turut untuk kolom yang berisi data panjang tetap, SQLGetData mengembalikan SQL_NO_DATA untuk semua panggilan setelah panggilan pertama.
Mengambil Parameter Output yang Dialirkan
Jika driver mendukung parameter output yang dialirkan, aplikasi dapat memanggil SQLGetData dengan buffer kecil berkali-kali untuk mengambil nilai parameter besar. Untuk informasi selengkapnya tentang parameter output yang dialirkan, lihat Mengambil Parameter Output Menggunakan SQLGetData.
Mengambil Data dengan SQLGetData
Untuk mengembalikan data untuk kolom yang ditentukan, SQLGetData melakukan urutan langkah-langkah berikut:
Mengembalikan SQL_NO_DATA jika sudah mengembalikan semua data untuk kolom.
Mengatur *StrLen_or_IndPtr ke SQL_NULL_DATA jika data null. Jika data null dan StrLen_or_IndPtr adalah pointer null, SQLGetData mengembalikan SQLSTATE 22002 (Variabel indikator diperlukan tetapi tidak disediakan).
Jika data untuk kolom bukan NULL, SQLGetData melanjutkan ke langkah 3.
Jika atribut pernyataan SQL_ATTR_MAX_LENGTH diatur ke nilai bukan nol, jika kolom berisi karakter atau data biner, dan jika SQLGetData sebelumnya belum dipanggil untuk kolom, data dipotong menjadi SQL_ATTR_MAX_LENGTH byte.
Catatan
Atribut pernyataan SQL_ATTR_MAX_LENGTH dimaksudkan untuk mengurangi lalu lintas jaringan. Ini umumnya diimplementasikan oleh sumber data, yang memotong data sebelum mengembalikannya di seluruh jaringan. Driver dan sumber data tidak diperlukan untuk mendukungnya. Oleh karena itu, untuk menjamin bahwa data dipotong ke ukuran tertentu, aplikasi harus mengalokasikan buffer dengan ukuran tersebut dan menentukan ukuran dalam argumen BufferLength .
Mengonversi data ke jenis yang ditentukan dalam TargetType. Data diberikan presisi dan skala default untuk jenis data tersebut. Jika TargetType SQL_ARD_TYPE, jenis data di bidang SQL_DESC_CONCISE_TYPE ARD digunakan. Jika TargetType SQL_ARD_TYPE, data diberi presisi dan skala dalam bidang SQL_DESC_DATETIME_INTERVAL_PRECISION, SQL_DESC_PRECISION, dan SQL_DESC_SCALE ARD, tergantung pada jenis data di bidang SQL_DESC_CONCISE_TYPE. Jika ada presisi atau skala default yang tidak sesuai, aplikasi harus secara eksplisit mengatur bidang deskriptor yang sesuai dengan panggilan ke SQLSetDescField atau SQLSetDescRec.
Jika data dikonversi ke jenis data panjang variabel, seperti karakter atau biner, SQLGetData memeriksa apakah panjang data melebihi BufferLength. Jika panjang data karakter (termasuk karakter penghentian null) melebihi BufferLength, SQLGetData memotong data menjadi BufferLength lebih sedikit panjang karakter penghentian null. Kemudian, data akan dihentikan null. Jika panjang data biner melebihi panjang buffer data, SQLGetData memotongnya menjadi byte BufferLength .
Jika buffer data yang disediakan terlalu kecil untuk menahan karakter penghentian null, SQLGetData mengembalikan SQL_SUCCESS_WITH_INFO dan SQLSTATE 01004.
SQLGetData tidak pernah memotong data yang dikonversi ke jenis data dengan panjang tetap; selalu mengasumsikan bahwa panjang *TargetValuePtr adalah ukuran jenis data.
Tempatkan data yang dikonversi (dan mungkin terpotong) di *TargetValuePtr. Perhatikan bahwa SQLGetData tidak dapat mengembalikan data dari baris.
Menempatkan panjang data dalam *StrLen_or_IndPtr. Jika StrLen_or_IndPtr adalah penunjuk null, SQLGetData tidak mengembalikan panjangnya.
Untuk data karakter atau biner, ini adalah panjang data setelah konversi dan sebelum pemotongan karena BufferLength. Jika driver tidak dapat menentukan panjang data setelah konversi, seperti halnya kadang-kadang dengan data panjang, driver mengembalikan SQL_SUCCESS_WITH_INFO dan mengatur panjang ke SQL_NO_TOTAL. (Panggilan terakhir ke SQLGetData harus selalu mengembalikan panjang data, bukan nol atau SQL_NO_TOTAL.) Jika data dipotong karena atribut pernyataan SQL_ATTR_MAX_LENGTH, nilai atribut ini - dibandingkan dengan panjang aktual - ditempatkan di *StrLen_or_IndPtr. Ini karena atribut ini dirancang untuk memotong data pada server sebelum konversi, sehingga driver tidak memiliki cara untuk mengetahui berapa panjang sebenarnya. Ketika SQLGetData dipanggil beberapa kali berturut-turut untuk kolom yang sama, ini adalah panjang data yang tersedia di awal panggilan saat ini; yaitu, panjangnya berkurang dengan setiap panggilan berikutnya.
Untuk semua jenis data lainnya, ini adalah panjang data setelah konversi; artinya, itu adalah ukuran jenis yang datanya dikonversi.
Jika data dipotong tanpa kehilangan signifikansi selama konversi (misalnya, angka riil 1,234 dipotong saat dikonversi ke bilangan bulat 1) atau karena BufferLength terlalu kecil (misalnya, string "abcdef" ditempatkan dalam buffer 4 byte), SQLGetData mengembalikan SQLSTATE 01004 (Data terpotong) dan SQL_SUCCESS_WITH_INFO. Jika data dipotong tanpa kehilangan signifikansi karena atribut pernyataan SQL_ATTR_MAX_LENGTH, SQLGetData mengembalikan SQL_SUCCESS dan tidak mengembalikan SQLSTATE 01004 (Data terpotong).
Konten buffer data terikat (jika SQLGetData dipanggil pada kolom terikat) dan buffer panjang/indikator tidak ditentukan jika SQLGetData tidak mengembalikan SQL_SUCCESS atau SQL_SUCCESS_WITH_INFO.
Panggilan berturut-turut ke SQLGetData akan mengambil data dari kolom terakhir yang diminta; offset sebelumnya menjadi tidak valid. Misalnya, ketika urutan berikut dilakukan:
SQLGetData(icol=n), SQLGetData(icol=m), SQLGetData(icol=n)
panggilan kedua ke SQLGetData(icol=n) mengambil data dari awal kolom n. Setiap offset dalam data karena panggilan sebelumnya ke SQLGetData untuk kolom tidak lagi valid.
Deskriptor dan SQLGetData
SQLGetData tidak berinteraksi langsung dengan bidang deskriptor apa pun.
Jika TargetType SQL_ARD_TYPE, jenis data di bidang SQL_DESC_CONCISE_TYPE ARD digunakan. Jika TargetType SQL_ARD_TYPE atau SQL_C_DEFAULT, data diberikan presisi dan skala dalam bidang SQL_DESC_DATETIME_INTERVAL_PRECISION, SQL_DESC_PRECISION, dan SQL_DESC_SCALE ARD, tergantung pada jenis data di bidang SQL_DESC_CONCISE_TYPE.
Contoh Kode
Dalam contoh berikut, aplikasi menjalankan pernyataan SELECT untuk mengembalikan kumpulan hasil ID pelanggan, nama, dan nomor telepon yang diurutkan menurut nama, ID, dan nomor telepon. Untuk setiap baris data, ia memanggil SQLFetch untuk memosisikan kursor ke baris berikutnya. Ini memanggil SQLGetData untuk mengambil data yang diambil; buffer untuk data dan jumlah byte yang dikembalikan ditentukan dalam panggilan ke SQLGetData. Terakhir, ini mencetak nama, ID, dan nomor telepon setiap karyawan.
#define NAME_LEN 50
#define PHONE_LEN 50
SQLCHAR szName[NAME_LEN], szPhone[PHONE_LEN];
SQLINTEGER sCustID, cbName, cbAge, cbBirthday;
SQLRETURN retcode;
SQLHSTMT hstmt;
retcode = SQLExecDirect(hstmt,
"SELECT CUSTID, NAME, PHONE FROM CUSTOMERS ORDER BY 2, 1, 3",
SQL_NTS);
if (retcode == SQL_SUCCESS) {
while (TRUE) {
retcode = SQLFetch(hstmt);
if (retcode == SQL_ERROR || retcode == SQL_SUCCESS_WITH_INFO) {
show_error();
}
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO){
/* Get data for columns 1, 2, and 3 */
SQLGetData(hstmt, 1, SQL_C_ULONG, &sCustID, 0, &cbCustID);
SQLGetData(hstmt, 2, SQL_C_CHAR, szName, NAME_LEN, &cbName);
SQLGetData(hstmt, 3, SQL_C_CHAR, szPhone, PHONE_LEN,
&cbPhone);
/* Print the row of data */
fprintf(out, "%-5d %-*s %*s", sCustID, NAME_LEN-1, szName,
PHONE_LEN-1, szPhone);
} else {
break;
}
}
}
Fungsi Terkait
Untuk informasi tentang | Lihat |
---|---|
Menetapkan penyimpanan untuk kolom dalam tataan hasil | SQLBindCol |
Melakukan operasi massal yang tidak terkait dengan posisi kursor blok | SQLBulkOperations |
Membatalkan pemrosesan pernyataan | SQLCancel |
Menjalankan pernyataan SQL | SQLExecDirect |
Menjalankan pernyataan SQL yang disiapkan | SQLExecute |
Mengambil blok data atau menggulir melalui kumpulan hasil | SQLFetchScroll |
Mengambil satu baris data atau blok data dalam arah terusan saja | SQLFetch |
Mengirim data parameter pada waktu eksekusi | SQLPutData |
Memosisikan kursor, merefresh data di himpunan baris, atau memperbarui atau menghapus data dalam set baris | SQLSetPos |
Lihat Juga
Referensi API ODBC
File Header ODBC
Mengambil Parameter Output Menggunakan SQLGetData