web-dev-qa-db-fra.com

Pourquoi une requête LIKE dans Access ne renvoie-t-elle aucun enregistrement?

Y a-t-il une raison pour laquelle

SELECT * FROM MyTable WHERE [_Items] LIKE '*SPI*'

ne renvoie aucun enregistrement avec OleDbAdapter.Fill(DataSet) ou OleDbCommand.ExecuteReader()?

Lorsque j'exécute directement le même code SQL dans MS Access, il renvoie les enregistrements attendus. En outre, dans le même code, si je change le SQL en

 SELECT * FROM MyTable 

tous les enregistrements sont retournés.

18
Jake

Changez votre * en % car % est la recherche générique lorsque vous utilisez OLE DB.

SELECT * FROM MyTable WHERE [_Items] LIKE '%SPI%' 
24
Neil Knight

Essayez de remplacer LIKE par ALIKE et vos caractères génériques de * à %.

Le moteur de base de données Access (Jet, ACE, peu importe) a deux modes de requête ANSI qui utilisent chacun des caractères génériques différents pour LIKE

  • Le mode de requête ANSI-89 utilise *

  • Le mode de requête ANSI-92 utilise %

OLE DB utilise toujours le mode de requête ANSI-92. DAO utilise toujours le mode de requête ANSI-89. L'interface utilisateur d'accès peut être configurée pour utiliser l'un ou l'autre.

Cependant, lorsque vous utilisez le mot clé ALIKE, le caractère générique est toujours %, quel que soit le mode de requête ANSI.

Considérons une règle de gestion qui stipule qu'un élément de données doit comporter exactement huit caractères numériques. Dites que j'ai mis en œuvre la règle comme suit:

CREATE TABLE MyStuff 
(
 ID CHAR(8) NOT NULL, 
 CHECK (ID NOT LIKE '%[!0-9]%')
);

Il est inévitable que j'utilise % comme caractère générique car le type de données CHAR et les contraintes CHECK d'Access ne peuvent être créés qu'en mode de requête ANSI-92.

Cependant, quelqu'un pourrait accéder à la base de données à l'aide de DAO, qui utilise toujours le mode de requête ANS-89, et le caractère % serait considéré comme un caractère littéral plutôt que 'spécial', et le code suivant pourrait être exécuté:

INSERT INTO MyStuff (ID) VALUES ('%[!0-9]%');

l'insertion réussirait et mon intégrité de données serait tirée :(

La même chose pourrait être dite en utilisant LIKE et * dans une règle de validation créée en mode de requête ANSI-89 et une personne qui se connecte à l'aide de ADO, qui utilise toujours le mode de requête ANSI-92, et INSERT un caractère * dans lequel un caractère * ne devrait pas être .

À ma connaissance, il n’existe aucun moyen de spécifier le mode de requête ANSI utilisé pour accéder à la base de données Access. Par conséquent, je pense que tout le code SQL doit être codé pour se comporter de manière cohérente, quel que soit le mode de requête ANSI choisi par l'utilisateur. 

Notez qu'il n'est pas trop difficile de coder pour les deux en utilisant LIKE avec l'exemple ci-dessus, par exemple. 

CHECK (
       ID NOT LIKE '%[!0-9]%'
       AND ID NOT LIKE '*[!0-9]*'
      )

... ou bien évitez complètement les jokers, par exemple 

CHECK (ID LIKE '[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]')

Cependant, utiliser ALIKE résultera en un code moins verbeux, c’est-à-dire plus facile pour le lecteur humain et donc plus facile à gérer. 

De plus, lorsque le moment est venu de mettre en communication un produit SQL conforme aux normes SQL, ALIKE est également utile, c’est-à-dire que la transformation du mot clé ALIKE en LIKE est tout ce qui est nécessaire. Lors de l'analyse d'un prédicat SQL donné, il est beaucoup plus facile de localiser le mot clé LIKE que de rechercher toutes les instances multiples du caractère * dans des littéraux de texte. Rappelez-vous que "portable" ne signifie pas que "le code fonctionnera tel quel"; c'est plutôt une mesure de la facilité avec laquelle il est possible de déplacer du code entre les plates-formes (et gardez à l'esprit que le passage d'une version à l'autre du même produit est un port, par exemple, Jet 4.0 à ACE est un port car la sécurité au niveau utilisateur ne fonctionne plus, valeurs DECIMAL trier différemment, etc.).

29
onedaywhen

Essayez de convertir vos caractères génériques (*) en%

Cela devrait régler le problème.

5
Pooli

Bon Dieu, ça marche! Merci beaucoup.

Il me suffisait de remplacer not like criteria par not alike criteria.

Je partage mon "histoire" pour aider les autres à trouver cet article plus facilement et à les sauver d'une recherche de deux heures.

Bien que j'ai lié les fichiers Excel 95-97 xls à la base de données Access 2010 et exécuté des requêtes create table et insert into pour importer toutes les données dans une base de données, pour une raison étrange, la requête de sélection n'a pas pu trouver les chaînes que j'ai saisies .

J'ai essayé not like "something" et not like "%something%" sans succès - cela n'a tout simplement pas fonctionné.

L

0
Levi