कंपाउंड ट्रिगर आज़माएं:
CREATE OR REPLACE TRIGGER compound_trigger_name
FOR INSERT OR UPDATE OF salary ON treballa
COMPOUND TRIGGER
TYPE Departments_t IS TABLE OF treballa.department%TYPE INDEX BY varchar2(100);
Departments Departments_t;
BEFORE EACH ROW IS
BEGIN
-- collect updated or inserted departments
Departments( :new.department ) := :new.department;
END BEFORE EACH ROW;
AFTER STATEMENT IS
sum_sal NUMBER;
BEGIN
-- for each updated department check the restriction
FOR dept IN Departments.FIRST .. Departments.LAST
LOOP
SELECT sum(salary) INTO sum_sal FROM treballa WHERE department = dept;
IF sum_sal > 1000 THEN
raise_application_error(-20123, 'The total salary for department '||dept||' cannot exceed 1000');
END IF;
END LOOP;
END AFTER STATEMENT;
END compound_trigger_name;
/
========संपादित करें - कुछ प्रश्न और उत्तर ==========
प्र:परिवर्तनशील तालिका त्रुटि क्यों होती है ?
उ:यह दस्तावेज़ीकरण में वर्णित है:
http://docs.oracle.com/cd/B28359_01/appdev.111/b28370/triggers.htm#g1699708
प्रश्न:परिवर्तनशील तालिका त्रुटि से कैसे बचें ?
उ:दस्तावेज़ीकरण एक कंपाउंड ट्रिगर के उपयोग की अनुशंसा करता है, इसे देखें:http://docs.oracle.com/cd/B28359_01/appdev.111/b28370/triggers.htm#CHDFEBFJ
प्र:कंपाउंड ट्रिगर क्या है और यह कैसे काम करता है ?
उ:यह एक बहुत बड़ा विषय है, कृपया यहां दस्तावेज़ देखें:http://docs.oracle.com/cd/B28359_01/appdev.111/b28370/triggers.htm#CIHEFGFD
संक्षेप में:यह एक विशेष प्रकार का ट्रिगर है जो चार प्रकार के अलग-अलग ट्रिगर्स को संयोजित करने योग्य बनाता है:ब्योरे से पहले
, पहले-प्रत्येक पंक्ति के लिए
, प्रत्येक पंक्ति के बाद
और स्टेटमेंट के बाद
एक घोषणा में। यह कुछ परिदृश्यों को लागू करना आसान बनाता है जिसमें कुछ डेटा को एक ट्रिगर से दूसरे ट्रिगर में पास करने की आवश्यकता होती है। अधिक विवरण के लिए कृपया उपरोक्त लिंक का अध्ययन करें।
प्रश्न:लेकिन वास्तव में "विभाग ( :new.department ) :=:new.department;
क्या करता है ?
A:यह डिक्लेरेशन डिपार्टमेंट नंबर को एक एसोसिएटिव ऐरे में स्टोर करता है।
यह ऐरे कंपाउंड ट्रिगर के डिक्लेरेटिव पार्ट में डिक्लेयर किया गया है:
TYPE Departments_t IS TABLE OF treballa.department%TYPE INDEX BY varchar2(100);
Departments Departments_t;
कंपाउंड ट्रिगर्स से संबंधित दस्तावेज़ कहता है कि:http ://docs.oracle.com/cd/B28359_01/appdev.111/b28370/triggers.htm#CIHJBEFE
उपरोक्त का अर्थ है कि विभाग
पूरी प्रक्रिया की शुरुआत में केवल एक बार वैरिएबल को इनिशियलाइज़ किया जाता है, ट्रिगर फ़ायर होने के ठीक बाद। "फायरिंग-स्टेटमेंट अवधि" का अर्थ है कि ट्रिगर खत्म होने के बाद यह वैरिएबल नष्ट हो जाता है। सहयोगी सरणी में एक विभाग संख्या संग्रहीत करता है। यह प्रत्येक पंक्ति से पहले
. में है अनुभाग, फिर इसे प्रत्येक पंक्ति के लिए निष्पादित किया जाता है जिसे अद्यतन/सम्मिलित विवरण द्वारा अद्यतन (या सम्मिलित) किया जाता है।:new
और :पुराना
छद्म रिकॉर्ड हैं, उन पर और अधिक आप यहां पा सकते हैं: http://docs.oracle.com/cd/E11882_01/appdev.112/e25519/triggers.htm#LNPLS99955
संक्षेप में::new.department
विभाग
. का एक नया मान प्राप्त करता है कॉलम- वर्तमान में अपडेट की गई पंक्ति के लिए (अपडेट किया गया मान - अपडेट के बाद), जबकि :old.department
इस कॉलम का पुराना मान देता है (अपडेट से पहले)।
इस संग्रह का उपयोग बाद में स्टेटमेंट के बाद
में किया जाता है। , जब ट्रिगर सभी अद्यतन विभागों को चुनते हैं (एक फॉर-लूप में), प्रत्येक विभाग के लिए सक्रिय होता है SUM(वेतन) चुनें ...
और फिर जांचता है कि क्या यह राशि 1000 से कम है
एक साधारण अपडेट पर विचार करें:अद्यतन ट्रेबल्ला सेट वेतन =वेतन + 10
. यह एक सिंगल अपडेट स्टेटमेंट है, लेकिन एक साथ कई पंक्तियों को बदल देता है। हमारे ट्रिगर के निष्पादन का क्रम इस प्रकार है:
- अपडेट स्टेटमेंट सक्रिय हो गया है:
अद्यतन ट्रेबल्ला सेट वेतन =वेतन + 10
- ट्रिगर का घोषणात्मक खंड निष्पादित किया जाता है, अर्थात:
विभाग
वैरिएबल इनिशियलाइज़ किया गया है प्रत्येक पंक्ति से पहले
अनुभाग को प्रत्येक अद्यतन पंक्ति के लिए अलग से निष्पादित किया जाता है - जितनी बार पंक्तियों को अद्यतन किया जाना है। इस स्थान पर हम सभी विभागों को बदली हुई पंक्तियों से एकत्रित करते हैं।कथन के बाद
अनुभाग निष्पादित किया जाता है। इस बिंदु पर तालिका पहले ही अपडेट हो चुकी है - सभी पंक्तियों में पहले से ही नया, अद्यतन वेतन है। हमविभागों
. में सहेजे गए विभागों के माध्यम से लूप करते हैं और हर एक के लिए हम जांचते हैं कि वेतन का योग 1000 के बराबर या कम है। यदि यह राशि इनमें से किसी भी विभाग के लिए> 1000 है, तो एक त्रुटि फेंक दी जाती है, और पूरा अपडेट निरस्त कर दिया जाता है और वापस ले लिया जाता है। अन्यथा ट्रिगर समाप्त हो जाता है, और अद्यतन किया जाता है (लेकिन आपको इन परिवर्तनों को वैसे भी करने की आवश्यकता है)।
प्र:एक साहचर्य सरणी क्या है, और अन्य संग्रहों (एक चर या एक नेस्टेड तालिका) के बजाय सिर्फ इस तरह के संग्रह का उपयोग क्यों किया जाता है?
A:PL/SQL संग्रह एक बहुत बड़ा विषय है। उन्हें जानने के लिए इस लिंक का अनुसरण करें:http:// docs.oracle.com/cd/E11882_01/appdev.112/e25519/composites.htm#LNPLS005
संक्षेप में - एसोसिएटिव ऐरे (या इंडेक्स-बाय टेबल) जावा (हैशमैप, ट्रेमैप आदि) में एक मैप की तरह है - यह की-वैल्यू पेयर का एक सेट है, और प्रत्येक कुंजी है अद्वितीय . आप इस सरणी में एक ही कुंजी को कई बार रख सकते हैं (अलग-अलग मानों के साथ), लेकिन यह कुंजी केवल एक बार संग्रहीत की जाएगी - यह अद्वितीय है।
मैंने इसका उपयोग विभागों का अनूठा सेट प्राप्त करने के लिए किया है।
हमारे अपडेट उदाहरण पर फिर से विचार करें:अद्यतन ट्रेबल्ला सेट वेतन =वेतन + 10
- यह कमांड उन सैकड़ों पंक्तियों को छूती है जिनमें एक ही विभाग होता है। मैं एक ही विभाग के साथ एक संग्रह को 100 बार डुप्लिकेट नहीं करना चाहता, मुझे विभागों के एक अद्वितीय सेट की आवश्यकता है, और मैं अपनी क्वेरी को निष्पादित करना चाहता हूं चुनें योग()...
प्रत्येक विभाग के लिए केवल एक बार, 100 बार नहीं। Sssociative सरणी की मदद से यह स्वचालित रूप से किया जाता है - मुझे विभागों का अनूठा सेट मिलता है।