سؤال

لماذا يستخدم '* لبناء رؤية سيئة؟

لنفترض أن لديك مجمع الانضمام إليها وكافة المجالات يمكن استخدامها في مكان ما.

وبعد ذلك عليك أن اختار الحقول المطلوبة.

SELECT field1, field2 FROM aview WHERE ...

والرأي "aview" يمكن SELECT table1.*, table2.* ... FROM table1 INNER JOIN table2 ...

لدينا مشكلة في حالة وجود 2 مجالات نفس الاسم في table1 و table2.

هل هذا هو السبب الوحيد لاستخدام "*" في طريقة عرض سيء؟

ومع '*'، قد استخدم طريقة العرض في سياق مختلف، لأن المعلومات هي هناك.

ما أنا في عداد المفقودين؟

والتحيات

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

المحلول

وأنا لا أعتقد أن هناك الكثير في البرامج التي هي "سيئة فقط"، ولكن هناك الكثير من الاشياء التي يساء استخدامها بطرق سيئة: -)

والمثال كنت تعطي هو السبب * قد لا تعطيك ما كنت تتوقع، وأعتقد أن هناك آخرين. على سبيل المثال، إذا تغيرت الجداول الأساسية، ربما يتم إضافة الأعمدة أو إزالتها، وهو رأي يستخدم * ستظل سارية المفعول، ولكن قد كسر أي التطبيقات التي تستخدمها. إذا وجهة نظركم كان اسمه الأعمدة صراحة بعد ذلك كان هناك اكثر من فرصة أن شخصا ما سوف بقعة المشكلة عند إجراء التغيير المخطط.

<الإضراب> من ناحية أخرى، قد فعلا <م> تريد عرض لبابتهاج قبول جميع التغييرات على الجداول الأساسية، وفي هذه الحالة سوف * يكون مجرد ما تريد.

تحديث: أنا لا أعرف إذا كان OP بائع قاعدة بيانات محددة في الاعتبار، ولكن من الواضح الآن أن بلدي مشاركة التصريح لا يحمل صحيحا بالنسبة لجميع أنواع. أنا مدين لuser12861 وجوني ليدز لافتا من ذلك، وآسف انها اتخذت أكثر من 6 سنوات بالنسبة لي لتعديل جوابي.

نصائح أخرى

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

وهناك سبب آخر لماذا "*" محفوف بالمخاطر، وليس فقط في وجهات النظر ولكن في الاستعلامات، هو أن الأعمدة يمكن تغيير اسم أو تغيير الموقف في الجداول الأساسية. باستخدام البدل يعني أن وجهة نظركم يستوعب هذه التغييرات بسهولة دون الحاجة إلى تغيير. ولكن إذا كان لديك مراجع التطبيق الأعمدة عن طريق وضع في مجموعة النتائج، أو إذا كنت تستخدم لغة ديناميكية وترجع مجموعات نتيجة مرتبطا بالاسم العمود، هل يمكن أن تواجه مشاكل التي يصعب التصحيح.

وأنا تجنب استخدام أحرف البدل في جميع الأوقات. وبهذه الطريقة إذا تغير عمود الاسم، أحصل على خطأ في طريقة العرض أو الاستعلام على الفور، وأنا أعرف من أين لإصلاحه. إذا تغير موقف عمود في الجدول المصدر، تحديد ترتيب الأعمدة في طريقة العرض أو يعوض الاستعلام لذلك.

وهذه الإجابات الأخرى جميعا النقاط الجيدة، ولكن على خادم SQL على الأقل لديهم أيضا بعض النقاط الخاطئة. جرب هذا:

create table temp (i int, j int)
go
create view vtemp as select * from temp
go
insert temp select 1, 1
go
alter table temp add k int
go
insert temp select 1, 1, 1
go
select * from vtemp

وSQL Server لا تعلم عن عمود "الجديد" عند إضافته. يمكن اعتمادا على ما تريد أن يكون هذا أمرا جيدا أو سيئا، ولكن في كلتا الحالتين هو على الأرجح ليست جيدة تعتمد على ذلك. وذلك لتجنب يبدو تماما مثل فكرة جيدة.

للي هذا السلوك الغريب هو السبب الأكثر إلحاحا لتجنب حدد * في وجهات النظر.

علمتني

والتعليقات التي الخلية لديها سلوك مماثل وأوراكل لا (سوف تتعلم حول تغييرات على الجدول). هذا التناقض بالنسبة لي هو مما يزيد من سبب لعدم استخدام حدد * في وجهات النظر.

<ع> استخدام "*" لإنتاج أي شيء سيء. انه لشيء رائع للاستعلامات لمرة واحدة، ولكن في رمز الإنتاج يجب أن تكون دائما واضحة قدر الإمكان.

لمشاهدة وجه الخصوص، إذا كانت الجداول الأساسية الأعمدة وأضافت أو إزالتها، فإن عرض إما أن تكون خاطئة أو مكسورة حتى يتم معاد له.

وعن طريق SELECT * داخل الرأي لا تحمل الكثير من النفقات العامة الأداء إذا لم يتم استخدام الأعمدة خارج الرأي - محسن وتحسين بها. SELECT * FROM TheView ربما يمكن عرض النطاق الترددي النفايات، تماما مثل أي وقت سحب أكثر من الأعمدة عبر اتصال شبكة.

في الواقع، لقد وجدت أن وجهات النظر التي تربط بين الأعمدة كلها تقريبا من عدد من الجداول ضخمة في بلدي مستودع البيانات لم تدخل أي مشكلات في الأداء في كل شيء، حتى من خلال عدد قليل نسبيا من تلك الأعمدة المطلوبة من خارج العرض. محسن يعالج بشكل جيد وقادرة على دفع معايير التصفية الخارجية وصولا إلى وجهة النظر بشكل جيد للغاية.

ولكن، لجميع الأسباب المذكورة أعلاه، وأنا نادرا ما تستخدم SELECT *.

ولدي بعض العمليات التجارية حيث يتم بناء عدد من CTEs على رأس كل منهما الآخر، وبناء فعال أعمدة المستمدة من أعمدة المستمدة من الأعمدة المشتقة (التي من المؤمل يوم واحد يجري إعادة بناء التعليمات كما ترشيد الأعمال وتبسيط هذه الحسابات)، و في هذه الحالة، وأنا في حاجة إلى كل الأعمدة لإسقاط من خلال كل الوقت، وأنا أستخدم SELECT * - ولكن SELECT * لم يتم استخدامها في طبقة الأساس، إلا في ما بين أول CTE وآخر

والوضع على SQL Server هو في الواقع أسوأ من الإجابة من طرف @ user12861 يعني: إذا كنت تستخدم SELECT * ضد جداول متعددة، إضافة الأعمدة إلى جدول المشار إليها في وقت مبكر من الاستعلام ستكون في الواقع سببا وجهة نظركم لإرجاع القيم من جديد الأعمدة تحت ستار من الأعمدة القديمة. انظر المثال التالي:

-- create two tables
CREATE TABLE temp1 (ColumnA INT, ColumnB DATE, ColumnC DECIMAL(2,1))
CREATE TABLE temp2 (ColumnX INT, ColumnY DATE, ColumnZ DECIMAL(2,1))
GO


-- populate with dummy data
INSERT INTO temp1 (ColumnA, ColumnB, ColumnC) VALUES (1, '1/1/1900', 0.5)
INSERT INTO temp2 (ColumnX, ColumnY, ColumnZ) VALUES (1, '1/1/1900', 0.5)
GO


-- create a view with a pair of SELECT * statements
CREATE VIEW vwtemp AS 
SELECT *
FROM temp1 INNER JOIN temp2 ON 1=1
GO


-- SELECT showing the columns properly assigned
SELECT * FROM vwTemp 
GO


-- add a few columns to the first table referenced in the SELECT 
ALTER TABLE temp1 ADD ColumnD varchar(1)
ALTER TABLE temp1 ADD ColumnE varchar(1)
ALTER TABLE temp1 ADD ColumnF varchar(1)
GO


-- populate those columns with dummy data
UPDATE temp1 SET ColumnD = 'D', ColumnE = 'E', ColumnF = 'F'
GO


-- notice that the original columns have the wrong data in them now, causing any datatype-specific queries (e.g., arithmetic, dateadd, etc.) to fail
SELECT *
FROM vwtemp
GO

-- clean up
DROP VIEW vwTemp
DROP TABLE temp2
DROP TABLE temp1

وانها لأنك لا تحتاج دائما كل متغير، وأيضا للتأكد من أن كنت تفكر في ما تريد على وجه التحديد.

وليس هناك نقطة الحصول على جميع كلمات السر المجزأة من قاعدة البيانات عند بناء قائمة من المستخدمين على موقع الويب الخاص بك على سبيل المثال، لذلك حدد * سيكون غير مثمر.

وذات مرة، أنا خلق رأي مقابل جدول في قاعدة بيانات أخرى (على نفس الخادم) مع

Select * From dbname..tablename

وبعد يوم واحد، تم إضافة عمود إلى الجدول مستهدفة. بدأ عرض إرجاع نتائج غير صحيحة تماما حتى تم نقلها إليها.


وغير صحيح تماما: لا الصفوف

وكان هذا على SQL Server 2000.

وأفترض أن هذا بسبب القيم syscolumns أن وجهة النظر ألقت القبض، على الرغم من أنني استخدمت *.

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

إذا كان لي أن تأتي على طول عامين من الآن مع الحاجة أو الرغبة في تغيير الاستعلام الخاص بك، وأتوقع أن جروك أنها جميلة جيدا قبل وأود أن تكون على ثقة من أنني أستطيع أن أعبر فوضى معها. وهو ما يعني أنني في حاجة إلى فهم لماذا تسمى كل الأعمدة خارج. (وهذا هو أكثر من الواضح صحيح إذا كنت تحاول إعادة الاستعلام في أكثر من سياق واحد. وهو مشكلة بشكل عام، لأسباب مماثلة.) إذا كان لي أن أرى الأعمدة في إخراج أنني لا يمكن أن تتصل بعض الأغراض ، وسأكون متأكد من أنني لم أفهم ما فعلته، ولماذا، وما هي العواقب ستكون من تغييره.

وانها عموما فكرة سيئة لاستخدام *. بعض محركات شهادة كود جعل مشاركات هذا بمثابة تحذير وننصح أن أشير صراحة فقط الأعمدة الضرورية. استخدام * يمكن أن يؤدي إلى أداء القمل كما قد تحتاج فقط بعض الأعمدة وليس كل شيء. ولكن، من ناحية أخرى، هناك بعض الحالات التي يكون فيها استخدام * مثالي. تخيل ذلك، مهما كانت، باستخدام المثال الذي قدمته، لهذا الرأي (aview) كنت في حاجة دائما كل الأعمدة في هذه الجداول. في المستقبل، عند إضافة عمود، فإنك لن تحتاج إلى تغيير طريقة العرض. وهذا يمكن أن تكون جيدة أو سيئة اعتمادا حال كنت تتعامل معه.

واعتقد ان ذلك يتوقف على اللغة التي تستخدمه. أنا أفضل أن استخدام حدد * عندما اللغة أو سائق DB بإرجاع ديكت (بايثون، بيرل، الخ) أو مجموعة النقابي (PHP) من النتائج. يجعل التعليمات البرمجية الكثير أسهل للفهم إذا كنت تقصد الأعمدة بالاسم بدلا من فهرس في صفيف.

ويبدو أن لا أحد قد ذكر ذلك، ولكن ضمن SQL Server الذي يمكن أن يحدد أيضا وجهة نظركم مع في SCHEMABINDING السمة .

وهذا يمنع تعديلات على أي من الجداول الأساسية (بما في ذلك إفلاتها) التي من شأنها أن تؤثر على تعريف الرأي.

وهذا قد يكون مفيدا لك في بعض الحالات. وأنا أدرك أنني لم تجب بالضبط سؤالك، ولكن يعتقد أن تسليط الضوء عليه مع ذلك.

وإذا كان لديك ينضم باستخدام حدد * يعني تلقائيا كنت ستعود المزيد من البيانات مما تحتاج كما هو تكرار البيانات في حقول الصلة. هذا هو الإسراف في قاعدة بيانات وشبكة الموارد.

إذا كنت ساذجا بما يكفي لاستخدام طرق العرض التي تدعو وجهات النظر الأخرى، وذلك باستخدام حدد * يمكن أن تجعل لهم أداء أسوأ من ذلك (وهذا هو الاسلوب الذي هو سيء للأداء من تلقاء نفسها، واصفا الأعمدة mulitple لا تحتاج يجعلها أسوأ بكثير ).

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