Oracle de nombre et de type varchar rejoindre
J'ai une requête qui joint deux tables. Une table a une colonne de type varchar, et de l'autre table a un type de numéro. J'ai exécuté ma requête sur 3 bases de données oracle, et je vois de drôles de résultats, je l'espère, peut être expliqué. Sur deux des bases de données de quelque chose comme les ouvrages suivants.
select a.col1, b.somecol
from tableA a inner join tableB b on b.col2=a.col1;
Dans cette requête tableA.col1 est de type nombre et la tableB.col2 est de type varchar. Cela fonctionne bien dans les deux bases de données, mais pas dans la troisième. Dans le troisième que j'obtiens (ORA-01722) erreur. Dans le troisième, j'ai besoin de faire quelque chose comme...
select a.col1, b.somecol
from tableA a inner join tableB b on b.col2=to_char(a.col1);
Cela fonctionne dans toutes les bases de données. La question que je me pose est pourquoi? Le ci-dessus est une forme simplifiée de la requête, et le réel de requête est un peu plus complexe et permet de retrouver un grand nombre de données, d'où la première version est beaucoup plus rapide. Si je pouvais obtenir que cela fonctionne dans tous les environnements, il serait grand.
Personne ne sait pourquoi, cela peut fonctionner dans certains des bases de données oracle et pas d'autres, sans le cast sur le type de données? Est-il un paramètre global qui permet un tel comportement?
Vous avez écrit tous ces mots et vous n'avez toujours pas réussi à expliquer précisément comment, la première requête qui ne fonctionne pas dans la troisième base de données.
Désolé, j'obtiens une erreur ORA-01722 erreur dans la première requête, le troisième de la base de données
J'ai donc deviné juste 😉
OriginalL'auteur broschb | 2010-02-24
Vous devez vous connecter pour publier un commentaire.
Une des raisons pourquoi les conversions implicites de l'échec, c'est quand le rejoindre colonne de type varchar contient des données qui n'est pas numérique. Oracle poignées nombre varchar2 rejoint par la conversion des chaînes de caractères (voir Gary citation dans son commentaire), de sorte qu'il s'exécute en fait à ceci :
Si tableB.col2 contient des valeurs qui ne sont pas numériques semble tout à fait probable, c'est une chaîne, après tout - il va lancer
ORA-01722: invalid number
. En faisant explicitement le casting du numéro de la colonne à une chaîne de court-circuit Oracle comportement par défaut.Le fait que vous n'aurez pas ce problème avec les deux premières environnements est une question de chance pas de configuration. Il peut frapper à tout moment, car il ne nécessite qu'un seul non-numérique chaîne de briser la requête. Si vraiment vous devez exécuter la conversion explicite dans tous les environnements.
Que pour la performance, vous pourriez construire une fonction d'index de base ...
Vous pouvez convertir le nombre en tableA à une chaîne de caractères au lieu de cela afin de ne pas obtenir les erreurs si il y a un non-chaîne numérique dans la tableB. ie CAST(un.col1 QUE VARCHAR(20))
OriginalL'auteur