Comment compter le nombre d'occurrences du caractère -
dans une chaîne varchar2?
Exemple:
select XXX('123-345-566', '-') from dual;
----------------------------------------
2
Voici:
select length('123-345-566') - length(replace('123-345-566','-',null))
from dual;
Techniquement, si la chaîne que vous voulez vérifier ne contient que le caractère que vous voulez compter, la requête ci-dessus retournera NULL; la requête suivante donnera la bonne réponse dans tous les cas:
select coalesce(length('123-345-566') - length(replace('123-345-566','-',null)), length('123-345-566'), 0)
from dual;
Le dernier 0 dans coalesce
attrape le cas où vous comptez dans une chaîne vide (c'est-à-dire NULL, car length (NULL) = NULL dans Oracle).
REGEXP_COUNT devrait faire l'affaire:
select REGEXP_COUNT('123-345-566', '-') from dual;
Voici une idée: essayez de remplacer tout ce qui n'est pas un caractère de tiret par une chaîne vide. Puis compte combien de tirets sont restés.
select length(regexp_replace('123-345-566', '[^-]', '')) from dual
J'ai pensé à
SELECT LENGTH('123-345-566') - LENGTH(REPLACE('123-345-566', '-', '')) FROM DUAL;
Je viens de faire face à un problème très similaire ... MAIS RegExp_Count n'a pas pu le résoudre . Combien de fois la chaîne '16, 124,3,3,1,0, 'contient', 3, '? Comme nous le voyons 2 fois, mais RegExp_Count ne retourne que 1. La même chose s’applique à '' bbaaaacc 'et lorsque vous y regardez' aa '- devrait être 3 fois et RegExp_Count ne renvoie que 2.
select REGEXP_COUNT('336,14,3,3,11,0,' , ',3,') from dual;
select REGEXP_COUNT('bbaaaacc' , 'aa') from dual;
J'ai perdu un peu de temps pour rechercher une solution sur le Web. Impossible de trouver ... donc j'ai écrit ma propre fonction qui renvoie le nombre TRUE réel. J'espère que ce sera utile.
CREATE OR REPLACE FUNCTION EXPRESSION_COUNT( pEXPRESSION VARCHAR2, pPHRASE VARCHAR2 ) RETURN NUMBER AS
vRET NUMBER := 0;
vPHRASE_LENGTH NUMBER := 0;
vCOUNTER NUMBER := 0;
vEXPRESSION VARCHAR2(4000);
vTEMP VARCHAR2(4000);
BEGIN
vEXPRESSION := pEXPRESSION;
vPHRASE_LENGTH := LENGTH( pPHRASE );
LOOP
vCOUNTER := vCOUNTER + 1;
vTEMP := SUBSTR( vEXPRESSION, 1, vPHRASE_LENGTH);
IF (vTEMP = pPHRASE) THEN
vRET := vRET + 1;
END IF;
vEXPRESSION := SUBSTR( vEXPRESSION, 2, LENGTH( vEXPRESSION ) - 1);
EXIT WHEN ( LENGTH( vEXPRESSION ) = 0 ) OR (vEXPRESSION IS NULL);
END LOOP;
RETURN vRET;
END;
voici une solution qui fonctionnera aussi bien pour les caractères que pour les sous-chaînes:
select (length('a') - nvl(length(replace('a','b')),0)) / length('b')
from dual
où a est la chaîne dans laquelle vous recherchez l'occurrence de b
bonne journée!
SELECT {FN LENGTH('123-345-566')} - {FN LENGTH({FN REPLACE('123-345-566', '#', '')})} FROM DUAL
select count(*)
from (
select substr('K_u_n_a_l',level,1) str
from dual
connect by level <=length('K_u_n_a_l')
)
where str ='_';