이 문서는 지원되지 않는 버전의 PostgreSQL을위한 것입니다.
당신은에 대해 같은 페이지를 보려고 할 수 있습니다PostgreSQL : 문서 : 17 : 41.13. Oracle 토토 사이트/SQL에서 포팅버전 또는 위에 나열된 다른 지원 버전 중 하나입니다.

39.12. 에서 포팅Oracle토토 사이트/sql

이 섹션은의 차이점을 설명합니다.PostgreSQL's토토 사이트/pgsql언어 및 Oracle 's토토 사이트/sql언어 의 응용 프로그램Oracle® topostgresql.

토토 사이트/pgsqlPL/SQL과 유사합니다 여러 측면에서. 블록 구조화되고 명령적인 언어이며 그리고 모든 변수는 선언되어야합니다. 과제, 루프, 조건부는 비슷합니다. 당신이 유지 해야하는 주요 차이점 에서 포팅 할 때 마음토토 사이트/sqlto토토 사이트/pgsqlare :

  • SQL 명령에 사용 된 이름이 열인 경우 테이블 이름 또는 함수 변수에 대한 참조토토 사이트/sql열로 취급합니다 이름. 이것은에 해당합니다.토토 사이트/pgsql's토토 사이트pgsql.variable_conflict=use_column기본값이 아닌 동작, 에 설명 된 바와 같이섹션 39.10.1. 그러한 모호성을 피하는 것이 가장 좋습니다 첫 번째 장소이지만 많은 양의 코드를 포트 해야하는 경우 그것은이 행동에 달려 있습니다variable_conflict최고 일 수 있습니다 해결책.

  • inPostgreSQL기능 본문은 문자열 문자로 작성해야합니다. 그러므로 달러 인용문을 사용하거나 단일 따옴표를 피해야합니다. 기능 본체. (보다섹션 39.11.1.)

  • 패키지 대신 스키마를 사용하여 구성하십시오 그룹으로의 기능.

  • 패키지가 없으므로 패키지 레벨이 없습니다 변수. 이것은 다소 성가시다. 당신은 유지할 수 있습니다 대신 임시 테이블의 세션 당 상태.

  • Integerfor루프Reverse다르게 작업 :토토 사이트/sql두 번째에서 카운트 하락합니다 첫 번째 숫자,토토 사이트/pgsql첫 번째에서 카운트 다운 루프 경계를 바꾸어야하는 두 번째 숫자 포팅 할 때. 이 비 호환성은 불행하지만 그렇습니다 변경되지 않을 것입니다. (보다섹션 39.6.3.5.)

  • for쿼리를 통해 루프 (기타 커서보다)도 다르게 작동합니다 : 대상 변수 (들) 선언되었지만토토 사이트/sql항상 암시 적으로 선언합니다. 이것의 장점은 변수 값이 여전히 루프가 종료 된 후에 액세스 할 수 있습니다.

  • 사용에는 다양한 표기법 차이가 있습니다 커서 변수.

39.12.1. 포팅 예제

예제 39-6간단한 기능을 포트하는 방법을 보여줍니다토토 사이트/sqlto토토 사이트/pgsql.

예 39-6. 에서 간단한 기능 포팅토토 사이트/sqltoPL/PGSQL

여기에Oracle 토토 사이트/sql기능 :

함수 작성 또는 교체 CS_FMT_BROWSER_VERSION (V_NAME VARCHAR,
                                                  v_version varchar)
반환 바르 르 차입니다
시작하다
    v_version이 null이면 그렇다면
        반환 v_name;
    끝 IF;
    반환 v_name || '/'|| v_version;
끝;
/
오류 표시;

이 기능을 살펴보고 차이점을 보자 에 비해토토 사이트/pgsql:

  • thereturn키워드 함수 프로토 타입 (기능 본문이 아님)이됩니다반환inPostgreSQL. 또한,isas, 그리고 당신은 a를 추가해야합니다.언어절로토토 사이트/pgsql유일한 기능 언어는 아닙니다.

  • inPostgreSQL, 기능 본문은 문자열 문자로 간주됩니다. 당신은 그 주변의 견적 마크 또는 달러 인용문을 사용해야합니다. 이것은 종료를 대신합니다/Oracle 접근법에서.

  • the오류 표시명령 존재하지 않음PostgreSQL, 오류 가보고되어 필요하지 않습니다 자동으로.

이것은이 기능이 포팅되었을 때 어떻게 보이는지입니다.PostgreSQL:

함수 작성 또는 교체 CS_FMT_BROWSER_VERSION (V_NAME VARCHAR,
                                                  v_version varchar)
Varchar를 $$로 반환합니다
시작하다
    v_version이 null이면 그렇다면
        반환 v_name;
    끝 IF;
    반환 v_name || '/'|| v_version;
끝;
$$ 언어 plpgsql;

예제 39-7다른 기능을 생성하는 함수를 포트하는 방법을 보여줍니다 기능 및 다음 인용 문제를 처리하는 방법.

예 39-7. 생성하는 함수를 포팅합니다 의 또 다른 함수토토 사이트/sqlto토토 사이트/pgsql

다음 절차는 a에서 행을 잡습니다.select진술 및 큰 기능을 구축합니다 결과와 함께if진술, 효율성을 위해.

이것은 Oracle 버전입니다 :

절차 작성 또는 교체 CS_UPDATE_REFERRER_TYPE_PROC IS
    Cursor referrer_keys입니다
        CS_REFERRER_KEYS에서 *를 선택하십시오
        try_order의 주문;
    func_cmd varchar (4000);
시작하다
    func_cmd : = '함수 생성 또는 교체 CS_FIND_REFERRER_TYPE (v_host in varchar,
                 Varchar의 V_Domain, Varchar의 V_URL) Return varchar가 시작됩니다. ';

    referrer_key의 경우 referrer_keys 루프
        func_cmd : = func_cmd ||
          'V_'|| referrer_key.kind
          || '좋아요' ''|| referrer_key.key_string
          || ````그런 다음 반환 '' '|| referrer_key.referrer_type
          || '' ';; 끝 If; ';
    엔드 루프;

    func_cmd : = func_cmd || '귀환 널; 끝;';

    즉시 func_cmd를 실행합니다.
끝;
/
오류 표시;

여기이 함수가 어떻게 끝날 것인지PostgreSQL:

함수 생성 또는 교체 CS_UPDATE_REFERRER_TYPE_PROC () voids는 $ func $로 void을 반환합니다
선언하다
    참조 _keys 커서입니다
        CS_REFERRER_KEYS에서 *를 선택하십시오
        try_order의 주문;
    func_body 텍스트;
    func_cmd 텍스트;
시작하다
    func_body : = '시작';

    referrer_key의 경우 referrer_keys 루프
        func_body : = func_body ||
          'V_'|| referrer_key.kind
          || '좋아요'|| quote_literal (referrer_key.key_string)
          || '그런 다음 반환'|| quote_literal (referrer_key.referrer_type)
          || ';; 끝 If; ' ;
    엔드 루프;

    func_body : = func_body || '귀환 널; 끝;';

    func_cmd : =
      '기능 생성 또는 교체 CS_FIND_REFERRER_TYPE (V_HOST VARCHAR,
                                                        v_domain varchar,
                                                        v_url varchar)
        varchar를 '로 반환합니다.
      || quote_literal (func_body)
      || '언어 plpgsql;' ;

    func_cmd를 실행합니다.
끝;
$ func $ language plpgsql;

함수의 본문이 어떻게 별도로 만들어 졌는지 알 수 있습니다. 그리고 통과quote_literalto 인용 표시가 두 배로 늘어납니다. 이 기술이 필요합니다 우리는 정의를 위해 달러 인용문을 안전하게 사용할 수 없기 때문에 새로운 기능 : 우리는 어떤 줄이 될지 확실하지 않습니다. 에서 보간referrer_key.key_string필드. (우리는 여기서referrer_key.kind항상 신뢰할 수 있습니다 BE호스트, 도메인또는url그러나referrer_key.key_string무엇이든, 특히 그것은 달러 표지판을 포함 할 수 있습니다.) 이것 기능은 실제로 Oracle Original의 개선입니다. 이 깨진 코드를 생성하지 않기 때문에referrer_key.key_string또는referrer_key.referrer_type견적을 포함하십시오 점수.

예제 39-8|out매개 변수 및 문자열 조작.PostgreSQLa 내장instr기능이지만 다른 기능의 조합을 사용하여 하나를 만들 수 있습니다. 안에섹션 39.12.3a토토 사이트/pgsql구현instr포팅에 사용할 수 있습니다 더 쉬운.

예 39-8. 문자열로 절차를 포팅합니다 조작 및out매개 변수PL/SQLto토토 사이트/pgsql

다음OraclePL/SQL 절차는 URL을 구문 분석하고 여러 반환하는 데 사용됩니다. 요소 (호스트, 경로 및 쿼리).

이것은 Oracle 버전입니다 :

절차 작성 또는 교체 CS_PARSE_URL (
    Varchar의 v_url,
    V_HOST OUT VARCHAR-- 이것은 다시 전달됩니다
    V_PATH OUT VARCHAR- - 이것도
    v_query out varchar) - 그리고 이것
이다
    A_POS1 정수;
    A_POS2 정수;
시작하다
    v_host : = null;
    v_path : = null;
    v_query : = null;
    a_pos1 : = inst (v_url, '//');

    A_POS1 = 0이면
        반품;
    끝 IF;
    a_pos2 : = inst (v_url, '/', a_pos1 + 2);
    a_pos2 = 0이면
        v_host : = substr (v_url, a_pos1 + 2);
        v_path : = '/';
        반품;
    끝 IF;

    v_host : = substr (v_url, a_pos1 + 2, a_pos2 -a_pos1-2);
    a_pos1 : = inst (v_url, '?', a_pos2 + 1);

    A_POS1 = 0이면
        v_path : = substr (v_url, a_pos2);
        반품;
    끝 IF;

    v_path : = substr (v_url, a_pos2, a_pos1 -a_pos2);
    v_query : = substr (v_url, a_pos1 + 1);
끝;
/
오류 표시;

여기에 가능한 번역이 있습니다토토 사이트/pgsql:

함수 작성 또는 교체 CS_PARSE_URL (
    Varchar의 v_url,
    V_HOST OUT VARCHAR-- 이것은 다시 전달됩니다
    V_PATH OUT VARCHAR- - 이것도
    v_query out varchar) - 그리고 이것
$$로
선언하다
    A_POS1 정수;
    A_POS2 정수;
시작하다
    v_host : = null;
    v_path : = null;
    v_query : = null;
    a_pos1 : = inst (v_url, '//');

    A_POS1 = 0이면
        반품;
    끝 IF;
    a_pos2 : = inst (v_url, '/', a_pos1 + 2);
    a_pos2 = 0이면
        v_host : = substr (v_url, a_pos1 + 2);
        v_path : = '/';
        반품;
    끝 IF;

    v_host : = substr (v_url, a_pos1 + 2, a_pos2 -a_pos1-2);
    a_pos1 : = inst (v_url, '?', a_pos2 + 1);

    A_POS1 = 0이면
        v_path : = substr (v_url, a_pos2);
        반품;
    끝 IF;

    v_path : = substr (v_url, a_pos2, a_pos1 -a_pos2);
    v_query : = substr (v_url, a_pos1 + 1);
끝;
$$ 언어 plpgsql;

이 기능은 다음과 같이 사용할 수 있습니다.

선택 *에서 CS_PARSE_URL ( 'http://foobar.com/query.cgi?baz');

예제 39-9다수를 사용하는 절차를 포트하는 방법을 보여줍니다 Oracle에 특화된 기능.

예 39-9. 절차 포팅PL/SQLtoPL/PGSQL

Oracle 버전 :

절차 작성 또는 교체 CS_CREATE_JOB (v_job_id)는 IS입니다
    a_running_job_count 정수;
    Pragma Autonomous_transaction;(1)시작
    독점 모드의 잠금 테이블 CS_JOBS;(2)cs_jobs에서 a_running_job_count로 count (*)를 선택하십시오.

    a_running_job_count 0 인 경우
        저지르다; - 무료 잠금(3)REAS_APPLICATION_ERROR (-20000,
                 '새로운 직업을 만들 수 없음 : 현재 일자리가 실행 중입니다.');
    끝 IF;

    cs_active_job에서 삭제;
    cs_active_job (job_id) 값 (v_job_id)에 삽입;

    시작하다
        cs_jobs (job_id, start_stamp) 값 (v_job_id, sysdate)에 삽입;
    예외
        dup_val_on_index 일 때 null; - 이미 존재하는지 걱정하지 마십시오
    끝;
    저지르다;
끝;
/
오류 표시

이와 같은 절차는 쉽게 변환 할 수 있습니다PostgreSQL기능 반환void. 이 절차는 특히 우리에게 일부를 가르쳐 줄 수 있기 때문에 특히 흥미 롭습니다 것들:

(1)
없음Pragma진술 안에PostgreSQL.
(2)
당신이 할 경우잠금 테이블in토토 사이트/pgsql, 자물쇠가 있습니다 호출 트랜잭션이 될 때까지 해제되지 않습니다 완성된.
(3)
당신은 발행 할 수 없습니다커밋in토토 사이트/pgsql함수. 그만큼 기능은 일부 외부 트랜잭션 내에서 실행 중입니다커밋종료를 의미합니다 함수의 실행. 그러나, 이것에서 어쨌든 자물쇠 때문에 필요하지 않습니다잠금 테이블의지 우리가 오류를 제기 할 때 풀려납니다.

이것이 우리 가이 절차를 포트 할 수있는 방법입니다토토 사이트/pgsql:

함수 생성 또는 교체 CS_CREATE_JOB (v_JOB_ID 정수)는 void를 $$로 반환합니다.
선언하다
    a_running_job_count 정수;
시작하다
    독점 모드에서 잠금 테이블 CS_JOBS;

    end_stamp가 null 인 cs_jobs에서 a_running_job_count로 count (*)를 선택하십시오.

    a_running_job_count 0 인 경우
        예외 제외 '새 작업을 만들 수 없음 : 현재 작업이 실행 중입니다';(1)종료 if;

    cs_active_job에서 삭제;
    cs_active_job (job_id) 값 (v_job_id)에 삽입;

    시작하다
        cs_jobs (job_id, start_stamp) 값 (v_job_id, now ())에 삽입;
    예외
        고유 _violation이있을 때(2)- 이미 존재하는지 걱정하지 마십시오
    끝;
끝;
$$ 언어 plpgsql;
(1)
의 구문Rainis 오라클의 진술과는 상당히 다릅니다 기본 케이스Raine Exception_name작품 비슷하게.
(2)
예외 이름이 지원하는토토 사이트/pgsql와 다릅니다 오라클. 내장 예외 이름 세트는 많습니다 더 큰 (참조Postgre토토 베이 : 문서). 현재 선언 할 방법은 없습니다 던질 수는 있지만 사용자 정의 예외 이름 사용자가 선택한 sqlstate 값 대신
이 절차 사이의 주요 기능적 차이 그리고 Oracle에 해당하는 것은에 대한 독점적 잠금입니다.CS_JOBS테이블은 전화 트랜잭션이 완료됩니다. 또한 발신자가 나중에 중단 (예 : 오류로 인해), 이것의 효과는 절차가 롤백됩니다.

39.12.2. 볼 다른 것들 을 위한

이 섹션은 언제 볼 수있는 몇 가지 다른 사항을 설명합니다. 포팅 오라클PL/SQL함수postgresql.

39.12.2.1. 암시 적 롤백 예외 후

in토토 사이트/pgsql, 언제 예외는에 의해 잡혔다.예외조항, 블록 이후 모든 데이터베이스 변경시작자동으로 롤백됩니다. 즉, 행동은 오라클에서 얻을 수있는 것과 같습니다. 와 함께:

시작
    SavePoint S1;
    ... 여기 코드 ...
예외
    언제 ... 그럼
        S1 롤백;
        ... 여기 코드 ...
    언제 ... 그럼
        S1 롤백;
        ... 여기 코드 ...
끝;

사용하는 Oracle 절차를 번역하는 경우SavePointand롤백으로이 스타일에서는 작업이 쉽습니다. 그냥 생략SavePointand롤백으로. 절차가있는 경우 사용SavePoint롤백으로다른 방식으로 일부 실제 생각이 필요합니다.

39.12.2.2. execute

the토토 사이트/pgsql버전execute와 유사하게 작동합니다PL/SQL버전이지만 있습니다 사용하는 것을 기억하려면quote_literalandQUOTE_INDEN설명대로섹션 39.5.4. 유형의 구성execute 'select * from $ 1';작동하지 않습니다 이러한 기능을 사용하지 않는 한 안정적으로.

39.12.2.3. 최적화PL/PGSQL기능

PostgreSQL두 가지를 제공합니다 실행 최적화를위한 기능 생성 수정 자 :"변동성"(함수 여부 동일한 인수가 주어지면 항상 같은 결과를 반환합니다) 그리고"엄격함"( 인수가 null이면 함수를 반환합니다). 상담기능 생성자세한 내용 참조 페이지.

이러한 최적화 속성을 사용할 때기능 생성진술이 보일 수 있습니다 다음과 같은 것 :

함수 생성 foo (...)는 정수를 $$로 반환합니다
...
$$ 언어 plpgsql 엄격한 불변성;

39.12.3. 충수

이 섹션에는 세트에 대한 코드가 포함되어 있습니다 오라클 호환instr함수 포팅 노력을 단순화하는 데 사용할 수 있습니다.

-
- Oracle의 상대를 모방하는 기기 기능
- 구문 : inst (String1, String2, [n], [m])는 []가 선택적 매개 변수를 나타냅니다.
-
-Mth 발생을 위해 Nth 캐릭터에서 시작하여 String1을 검색합니다.
- String2.  n이 음수이면 뒤로 검색하십시오.  M이 통과되지 않으면
- 1이라고 가정합니다 (첫 번째 문자에서 검색이 시작됩니다).
-

기능 악기 (Varchar, Varchar)를 작성하십시오. 정수를 $$로 반환합니다
선언하다
    POS 정수;
시작하다
    POS : = 기기 ($ 1, $ 2, 1);
    POS 리턴;
끝;
$$ 언어 plpgsql 엄격한 불변;

기능 악기 만들기 (String varchar, String_to_search varchar, beg_index 정수)
정수를 $$로 반환합니다
선언하다
    POS 정수 NOL NULL DEFAULT 0;
    temp_str varchar;
    정수를 구걸하십시오.
    길이 정수;
    ss_length 정수;
시작하다
    beg_index 0이면
        temp_str : = substring (beg_index의 문자열);
        pos : = 위치 (temp_str의 String_to_search);

        POS = 0이면
            반환 0;
        또 다른
            POS + BEG_INDEX를 반환합니다 -1;
        끝 IF;
    또 다른
        ss_length : = char_length (String_to_search);
        길이 : = char_length (문자열);
        beg : = 길이 + beg_index -ss_length + 2;

        beg 0 루프
            temp_str : = 서브 스트링 (ss_length의 beg에서 문자열);
            pos : = 위치 (temp_str의 String_to_search);

            POS 0이라면
                반환 구걸;
            끝 IF;

            Beg : = Beg -1;
        엔드 루프;

        반환 0;
    끝 IF;
끝;
$$ 언어 plpgsql 엄격한 불변;

기능 악기 생성 (String varchar, String_to_search Varchar,
                      beg_index 정수, cose_index 정수)
정수를 $$로 반환합니다
선언하다
    POS 정수 NOL NULL DEFAULT 0;
    alkes_number 정수 NOL NULL DEFAULT 0;
    temp_str varchar;
    정수를 구걸하십시오.
    나는 정수;
    길이 정수;
    ss_length 정수;
시작하다
    beg_index 0이면
        beg : = beg_index;
        temp_str : = substring (beg_index의 문자열);

        1. Occur_index 루프
            pos : = 위치 (temp_str의 String_to_search);

            I = 1이면
                beg : = beg + pos -1;
            또 다른
                beg : = beg + pos;
            끝 IF;

            temp_str : = 서브 스트링 (beg + 1의 문자열);
        엔드 루프;

        POS = 0이면
            반환 0;
        또 다른
            반환 구걸;
        끝 IF;
    또 다른
        ss_length : = char_length (String_to_search);
        길이 : = char_length (문자열);
        beg : = 길이 + beg_index -ss_length + 2;

        beg 0 루프
            temp_str : = 서브 스트링 (ss_length의 beg에서 문자열);
            pos : = 위치 (temp_str의 String_to_search);

            POS 0이라면
                alkes_number : = alkes_number + 1;

                alke_number = cose_index가있는 경우
                    반환 구걸;
                끝 IF;
            끝 IF;

            Beg : = Beg -1;
        엔드 루프;

        반환 0;
    끝 IF;
끝;
$$ 언어 plpgsql 엄격한 불변성;