سؤال

كيف يمكنني إنشاء Oracle تخزين الإجراء الذي يقبل عدد متغير من قيم المعلمات المستخدمة لإطعام في الحدوث ؟

هذا هو ما أحاول تحقيقه.أنا لا أعرف كيف أن تعلن في PLSQL تمرير متغير قائمة المفاتيح الأساسية من الصفوف أريد أن التحديث.

FUNCTION EXECUTE_UPDATE
  ( <parameter_list>
   value IN int)
  RETURN  int IS
BEGIN 
    [...other statements...]
    update table1 set col1 = col1 - value where id in (<parameter_list>) 

    RETURN SQL%ROWCOUNT ;
END;

أيضا أود أن استدعاء هذا الإجراء من C#, لذلك يجب أن تكون متوافقة مع .صافي القدرات.

شكرا روبرت

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

المحلول

وعن طريق CSV وربما كان أبسط طريقة، على افتراض انك يمكن أن تكون 100٪ على يقين من أن عناصر الخاص بك لن أنفسهم تحتوي على سلاسل.

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

CREATE TYPE string_table AS TABLE OF varchar2(100);

وبعد ذلك يمكنك تمرير متغير من هذا النوع في الإجراء المخزن الخاص بك والرجوع إليه مباشرة. في حالتك، شيء من هذا القبيل:

FUNCTION EXECUTE_UPDATE(
    identifierList string_table,
    value int)
RETURN int
IS
BEGIN

    [...other stuff...]

    update table1 set col1 = col1 - value 
    where id in (select column_value from table(identifierList));

    RETURN SQL%ROWCOUNT;

END

وظيفة table() تتحول النوع المخصص الخاص بك إلى جدول مع عمود "COLUMN_VALUE" واحد، والتي يمكن بعد ذلك علاج مثل أي جدول آخر (حتى لا ينضم أو، في هذه الحالة، subselects).

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

execute_update(string_table('foo','bar','baz'), 32);

وأفترض أنه يمكنك التعامل مع بناء هذا الأمر برمجيا من C #.

وبوصفها جانبا، في الشركة التي أعمل لدينا عدد من هذه الأنواع المخصصة المحددة وفقا لمعايير قوائم الجمل، والزوجي، [إينتس] وهلم جرا. نحن أيضا الاستفادة من أوراكل JPublisher لتكون قادرة على الخريطة مباشرة من هذه الأنواع إلى كائنات جافا المقابلة. كان لي نظرة سريعة حول ولكن لم أستطع أن أرى أي معادلات مباشرة لC #. بس كنت أذكر أنه في حالة المشروعات الإنمائية جافا تأتي عبر هذا السؤال.

نصائح أخرى

ولقد وجدت المقال التالي الذي كتبه مارك A. وليامز التي أرى أنها ستكون إضافة مفيدة لهذا الموضوع. المادة يعطي مثالا جيدا لتمرير صفائف من C # لprocs / SQL PL باستخدام صفائف النقابي (TYPE myType هو جدول INDEX mytable.row٪ حسب نوع PLS_INTEGER):

المادة العظمى مارك وليامز A.

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

  1. إذا كان هناك بعض نموذجية أنواع الاتصال الداخلي الحمولة الزائدة قد تساعد.
  2. إذا كان هناك حد أعلى في عدد من المعلمات (و النوع كما هو معروف مقدما), القيم الافتراضية من المعلمات قد تساعد.
  3. الخيار الأفضل هو ربما استخدام المؤشر المتغيرات ما هي مؤشرات إلى قاعدة بيانات المؤشرات.

للأسف ليس لدي أي خبرة .صافي البيئات.

لماذا لا مجرد استخدام قائمة المعلمة طويلة وتحميل القيم في منشئ الطاولة؟ هنا هو SQL / PSM لهذه الخدعة

UPDATE Foobar
   SET x = 42
 WHERE Foobar.keycol
      IN (SELECT X.parm
            FROM (VALUES (in_p01), (in_p02), .., (in_p99)) X(parm)
           WHERE X.parm IS NOT NULL);

وماذا عليها أن يكون الإجراء المخزن؟ هل يمكن بناء بيان معد برمجيا.

ولقد تكن قد فعلت ذلك لأوراكل، ولكن مع SQL Server يمكنك استخدام دالة لتحويل سلسلة CSV في جدول، والتي يمكن استخدامها بعد ذلك في جملة IN. وينبغي أن يكون مستقيم الى الامام لإعادة كتابة هذه لأوراكل (على ما أظن!)

CREATE Function dbo.CsvToInt ( @Array varchar(1000)) 
returns @IntTable table 
    (IntValue nvarchar(100))
AS
begin

    declare @separator char(1)
    set @separator = ','

    declare @separator_position int 
    declare @array_value varchar(1000) 

    set @array = @array + ','

    while patindex('%,%' , @array) <> 0 
    begin

      select @separator_position =  patindex('%,%' , @array)
      select @array_value = left(@array, @separator_position - 1)

        Insert @IntTable
        Values (Cast(@array_value as nvarchar))

      select @array = stuff(@array, 1, @separator_position, '')
    end

    return
end

وبعد ذلك يمكنك تمرير في سلسلة CSV (على سبيل المثال "0001،0002،0003 ') وتفعل شيئا مثل

UPDATE table1 SET 
       col1 = col1 - value 
WHERE id in (SELECT * FROM csvToInt(@myParam)) 

وهناك مقال على موقع على شبكة الإنترنت AskTom يوضح كيفية إنشاء دالة تحليل سلسلة CSV واستخدام ذلك في بيانكم بطريقة مشابهة للمثال SQL خادم معين.

وانظر <لأ href = "http://asktom.oracle.com/pls/asktom/f؟p=100:11:0::::P11_QUESTION_ID:139812348065" يختلط = "نوفولو noreferrer" عنوان = "ASkTom "> Asktom

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