2010-02-01 4 views
2

Как написать цикл, который имеет выбор в разделе «in» цикла, который выбирает col типа varchar(10), но затем вставляет эти значения в col что хочет, чтобы они были varchar(9)? В принципе, я пытаюсь «придумать» из одной точности в другую, если это имеет смысл. Пример:PL/SQL varchar (10) to varchar (9)

FOR V_TEN IN (SELECT THIS_IS_VARCHAR_TEN FROM TABLE WHERE SOMETHING=’VALUE’) 
LOOP 
       INSERT INTO OTHER_TABLE 
       (THIS_IS_VARCHAR_NINE) 
       VALUES 
       (V_TEN); 
END LOOP; 

Ошибка в том, что типы столбцов не совпадают. Я пробовал посмотреть на to_char() и cast(), но, похоже, я не хочу этого делать. Я понимаю, что здесь есть потеря точности, и все в порядке с этим, так как я действительно знаю, что значения в столбце varchar(10) всегда будут 9 символов.

+0

Почему вы не делаете то, что хотите? – lins314159

ответ

1

Использование:

FOR V_TEN IN (SELECT SUBSTR(t.this_is_varchar_ten, 1, 9) 
       FROM TABLE t 
       WHERE t.something = 'VALUE') 
LOOP 

    INSERT INTO OTHER_TABLE 
    (THIS_IS_VARCHAR_NINE) 
    VALUES 
    (V_TEN); 

END LOOP; 

Используйте функцию SUBSTR для подстроки в VARCHAR (10) данных, так что возвращается как VARCHAR (9)

10

Вы ищете функции SUBSTR.

Кроме того, не используйте PL/SQL для этого, простой SQL будет делать и быть быстрее.

INSERT INTO OTHER_TABLE 
    SELECT OTHER_COLUMN, SUBSTR(THIS_IS_VARCHAR_TEN,1,9) 
    FROM TABLE WHERE SOMETHING=’VALUE’; 

И если действительно нет значения больше, чем девять характера, вы не должны даже вызвать функцию SubStr (она будет автоматически конвертирована и вызвать ошибку, если слишком долго).

+0

+1 для использования SQL, а не цикла PL/SQL. – APC

4

, так как я на самом деле знаю, что значения в VARCHAR колонка (10) всегда будут 9 символов.

Если это правда, тогда вам даже не нужно использовать SUBSTR, как предлагали другие.

Я считаю, что причина, по которой вы получаете сообщение об ошибке, заключается в том, что вы пытаетесь вставить значение V_TEN. Когда вы используете конструкцию типа FOR x IN (SELECT ...) LOOP, x неявно объявляется типом записи. В вашем случае это запись только с одним полем, но вы по-прежнему не можете использовать ее непосредственно в виде скалярного типа.

Вам просто нужно указать поле записи по имени в своей вставке.

FOR V_TEN IN (SELECT THIS_IS_VARCHAR_TEN FROM TABLE WHERE SOMETHING=’VALUE’) 
LOOP 
       INSERT INTO OTHER_TABLE 
       (THIS_IS_VARCHAR_NINE) 
       VALUES 
       (V_TEN.THIS_IS_VARCHAR_TEN); 
END LOOP; 

В любом случае, как Тило указал, что нет никаких причин, чтобы сделать это в явном цикле вообще. Просто напишите его как единственный INSERT ... SELECT.