web-dev-qa-db-fra.com

Fonctions vs procédures dans Oracle

quelqu'un peut-il expliquer quelle est la principale différence entre les fonctions et les procédures dans Oracle? Pourquoi dois-je utiliser des procédures si je peux tout faire avec des fonctions?

  1. Si je ne peux pas appeler la procédure dans l'instruction SQL, d'accord, j'écrirai une fonction pour effectuer le même travail.
  2. Les procédures ne renvoient pas de valeurs, ok, je ne renverrai que sql% rowcount ou 1 (succès), 0(exception) après toute opération dml
  3. Les procédures et les fonctions peuvent transmettre des variables à l'environnement d'appel via les paramètres OUT/IN OUT

J'ai entendu dire que la différence principale réside dans les performances: "les procédures sont plus rapides que les fonctions". Mais sans aucun détail.

Merci d'avance.

46
0bj3ct

La différence est- Une fonction doit renvoyer une valeur (de tout type) par définition, alors que dans le cas d'une procédure, vous devez utiliser des paramètres tels que OUT ou IN OUT paramètres pour obtenir les résultats. Vous pouvez utiliser une fonction dans un SQL normal où vous ne pouvez pas utiliser de procédure dans les instructions SQL.

Quelques différences entre les fonctions et les procédures

  1. Une fonction renvoie toujours une valeur à l'aide de l'instruction return, tandis qu'une procédure peut renvoyer une ou plusieurs valeurs par le biais de paramètres ou peut ne pas renvoyer du tout.Bien que les paramètres OUT puissent toujours être utilisés dans des fonctions, ils ne sont pas conseillés non plus. il y a des cas où on pourrait trouver un besoin de le faire. L'utilisation du paramètre OUT empêche une fonction d'être utilisée dans une instruction SQL.

  2. Des fonctions peuvent être utilisées dans des instructions SQL typiques telles que SELECT, INSERT, UPDATE, DELETE, MERGE, alors que les procédures ne le peuvent pas.

  3. Les fonctions sont normalement utilisées pour les calculs où les procédures sont normalement utilisées pour exécuter la logique applicative.

  4. Oracle fournit la possibilité de créer " Index basés sur les fonctions " pour améliorer les performances de l'instruction SQL suivante. Ceci s'applique lors de l'exécution de la fonction sur une colonne indexée dans la clause where d'une requête.

Plus d'informations sur les fonctions vs. Procédures ici et ici .

48
Romo Daneghyan

Il n'y a presque jamais de différence de performance entre les procédures et les fonctions.

Dans quelques cas extrêmement rares:

  • Une procédure IN OUT l'argument est plus rapide qu'un retour de fonction, lorsque l'inline est activée.
  • Une procédure IN OUT l'argument est plus lent qu'un retour de fonction, lorsque l'inline est désactivée.

Code de test

--Run one of these to set optimization level:
--alter session set plsql_optimize_level=0;
--alter session set plsql_optimize_level=1;
--alter session set plsql_optimize_level=2;
--alter session set plsql_optimize_level=3;

--Run this to compare times.  Move the comment to enable the procedure or the function.
declare
    v_result varchar2(4000);

    procedure test_procedure(p_result in out varchar2) is
    begin
        p_result := '0123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789';
    end;

    function test_function return varchar2 is
    begin
        return '0123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789';
    end;
begin
    for i in 1 .. 10000000 loop
        --Comment out one of these lines to change the test.
        --test_procedure(v_result);
        v_result := test_function;
    end loop;
end;
/

Résultats

Inlining enabled:  PLSQL_OPTIMIZE_LEVEL = 2 (default) or 3
Function  run time in seconds: 2.839, 2.933, 2.979
Procedure run time in seconds: 1.685, 1.700, 1.762

Inlining disabled: PLSQL_OPTIMIZE_LEVEL = 0 or 1
Function  run time in seconds:  5.164, 4.967, 5.632
Procedure run time in seconds: 6.1, 6.006, 6.037

Le code ci-dessus est trivial et peut-être soumis à d'autres optimisations. Mais j'ai vu des résultats similaires avec le code de production.

Pourquoi la différence n'a pas d'importance

Ne regardez pas le test ci-dessus et pensez "une procédure est deux fois plus rapide qu'une fonction!". Oui, les frais généraux d'une fonction sont presque deux fois plus importants que ceux d'une procédure. Mais dans tous les cas, les frais généraux sont négligeables.

La clé des performances de la base de données consiste à effectuer le plus de travail possible dans les instructions SQL, par lots. Si un programme appelle une fonction ou une procédure dix millions de fois par seconde, ce programme rencontre de graves problèmes de conception.

14
Jon Heller

Changement d'état ou non-changement d'état

En plus de réponse de Romo Daneghyan , j'ai toujours considéré la différence comme leur comportement dans l'état du programme. C'est-à-dire conceptuellement,

  • Les procédures peuvent modifier certains états, que ce soit des paramètres ou de l'environnement (par exemple, des données dans des tableaux, etc.).
  • Les fonctions ne changent pas d'état, et vous vous attendriez à ce que l'appel d'une fonction particulière ne modifie aucune donnée/état. (Par exemple, le concept sous-jacent programmation fonctionnelle )

En d'autres termes, si vous appelez une fonction nommée generateId(...), vous vous attendez à ce qu'elle ne fasse que des calculs et renvoie une valeur. Mais appeler une procédure generateId ..., vous pouvez vous attendre à ce qu'il change des valeurs dans certaines tables.

Bien sûr, il semble que dans Oracle ainsi que dans de nombreuses langues, cela ne s'applique pas et n'est pas appliqué, alors c'est peut-être juste moi.

9
typoerrpr
  1. La procédure peut ou non renvoyer une valeur, mais les fonctions renvoient une valeur.

  2. procedure use out paramètre returnvalue but but function mais returnstatment fournit.

  3. procédure utilisée manipulation des données mais fonction utiliser calcul des données.
  4. le temps d'exécution de la procédure n'utilise pas l'instruction select mais l'instruction use use select. Ce sont la différence majeure de celui-ci.
2
dinesh

C’est une excellente question à laquelle il n’a pas vraiment été répondu. La question n'est pas "Quelle est la différence entre une fonction et une procédure?" C'est plutôt "Pourquoi utiliserais-je jamais une procédure quand je peux faire la même chose avec une fonction?"

Je pense que la vraie réponse est "C’est une convention." Et comme c’est la convention, c’est ce à quoi les autres développeurs sont habitués et s’attendent, vous devez donc suivre convention. Mais il n'y a aucune raison fonctionnelle d'écrire un sous-programme en tant que procédure sur une fonction. La seule exception peut être lorsqu'il y a plusieurs paramètres OUT.

Dans son 6ème édition de la programmation Oracle PL/SQL , Steven Feuerstein vous recommande de réserver OUT et IN OUT paramètres pour les procédures et renvoyer uniquement des informations dans les fonctions via la clause RETURN (p. 612). Mais encore une fois, la raison en est la convention. Les développeurs ne s'attendent pas à ce que les fonctions aient des paramètres OUT.

J’ai écrit un post longish here arguant que vous ne devriez utiliser une procédure que si une fonction ne fait pas le travail. Personnellement, je préfère les fonctions et souhaite que la convention utilise les fonctions par défaut, mais je pense qu'une meilleure pratique consiste à accepter les choses que je ne peux pas changer et me plier à la convention réelle et non à celle que j'ai souhaiterais pour.

1
Webucator