سؤال

متابعة لأحد أسئلتي السابقة للقيام بها تصميم الطريقة لقد نصحت بتنفيذ استعلامات SQL الخاصة بي كاستعلام ذي معلمات بدلاً من سلسلة بسيطة.

لم أستخدم مطلقًا استعلامات ذات معلمات من قبل، لذلك قررت أن أبدأ بشيء بسيط، وهو ما يلي يختار إفادة:

String select = "SELECT * FROM ? ";

PreparedStatement ps = connection.prepareStatement(select);
ps.setString(1, "person");

هذا يعطيني الخطأ التالي: "[SQLITE_ERROR] خطأ SQL أو قاعدة بيانات مفقودة (بالقرب من "؟":خطأ في بناء الجملة)"

ثم قمت بتجربة نسخة معدلة تحتوي على معايير إضافية؛

String select = "SELECT id FROM person WHERE name = ? ";

PreparedStatement ps = connection.prepareStatement(select);
ps.setString(1, "Yui");

يعمل هذا الإصدار بشكل جيد، في المثال الأول، هل أفتقد نقطة الاستعلامات ذات المعلمات أم أنني أقوم بإنشائها بشكل غير صحيح؟

شكرًا!

هل كانت مفيدة؟

المحلول

ببساطة، لا يمكن لربط SQL ربط الجداول، فقط حيث تكون قيم الجملة.هناك بعض الأسباب الفنية الكامنة وراء ذلك والمتعلقة بـ "تجميع" عبارات SQL المعدة.بشكل عام، تم تصميم الاستعلامات ذات المعلمات لجعل SQL أكثر أمانًا عن طريق منع حقن SQL وكان لها فائدة جانبية تتمثل في جعل الاستعلامات أكثر "نمطية" أيضًا ولكن ليس إلى حد القدرة على تعيين اسم الجدول ديناميكيًا (نظرًا لأنه من المفترض أنك تعرف بالفعل ما سيكون عليه الجدول).

نصائح أخرى

إذا كنت تريد كافة الصفوف من جدول PERSON، فإليك ما يجب عليك فعله:

String select = "SELECT * FROM person";

PreparedStatement ps = connection.prepareStatement(select);

لا يؤدي ربط المتغير إلى ربط أسماء الجداول ديناميكيًا كما هو مذكور أعلاه.إذا كان اسم الجدول يأتي إلى طريقتك كمتغير، فيمكنك إنشاء الاستعلام بالكامل على النحو التالي:

String select = "SELECT * FROM " + varTableName;
PreparedStatement ps = connection.prepareStatement(select);

الاستعلامات ذات المعلمات مخصصة للاستعلام عن أسماء الحقول - وليس اسم الجدول!

لا تزال البيانات المعدة SQL ويجب إنشاؤها باستخدام عبارة المكان المناسبة؛أي.حيث س = ص.إحدى مزاياها هي أنه يتم تحليلها بواسطة RDMS عند رؤيتها لأول مرة، بدلاً من كل مرة يتم إرسالها فيها، مما يؤدي إلى تسريع عمليات التنفيذ اللاحقة لنفس الاستعلام بقيم ربط مختلفة.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top