Получить строку между двумя конкретными позициями символов
У меня есть длинная текстовая строка в SAS, и значение внутри него переменной длины, но всегда сопровождается символом "#" и затем заканчивается символом ","
Есть ли способ, которым я могу извлечь это и сохранить как новую переменную, пожалуйста?
например: слово слово, слово, № 12.34, слово, слово
И я хочу получить 12,34
Спасибо!
5 ответов
Двойное сканирование также должно работать, если у вас есть только один #
:
data _null_;
var1 = 'word word, word, #12.34, word, word';
var2 = scan(scan(var1,2,'#'),1,',');
put var2=;
run;
Вы можете использовать substr
а также index
функции, чтобы сделать это. index
функция возвращает первую позицию указанного символа.
data _null_;
var1 = 'word word, word, #12.34, word, word';
pos1 = index(var1,'#'); *Get the position of the first # sign;
tmp = substr(var1,pos1+1); *Create a string that returns only characters after the # sign;
put tmp;
pos2 = index(tmp,','); *Get the position of the first "," in the tmp variable;
var2 = substr(tmp,1,pos2-1);
put var2;
run;
Обратите внимание, что этот метод работает, только если в строке есть только один "#".
Еще один способ сделать это с помощью Regex и код приведен ниже
data have;
infile datalines truncover ;
input var $200.;
datalines;
word word, word, #12.34, word, word
word1 #12.34, hello hi hello hi
word1 #970000 hello hi hello hi #970022, hi
word1 123, hello hi hello hi #97.99
#99456, this is cool
;
Небольшая заметка о ниже регулярных выражений и функций
(?<=#) Позитивное утверждение с нулевой шириной и поиск # перед образцом интереса
(\d+.?\d+) здесь означает цифру, за которой следует или не следует. и другие цифры
(?=,) Позитивное упреждающее утверждение нулевой ширины и поиск по интересующему образцу
Вызов prxsubstr находит положение и длину шаблона, а substr извлекает требуемые значения.
data want( drop=pattern position length);
retain pattern;
IF _N_ = 1 THEN PATTERN = PRXPARSE("/(?<=#)(\d+\.?\d+)(?=,)/");
set have;
call prxsubstr(pattern, var, position, length);
if position then
match = substr(var, position, length);
run;
Одним из способов является использование index
определить местонахождение двух "стражей", разграничивающих значение, и получить данные с помощью substr
, Если значение должно быть числовым, дополнительное использование input
функция нужна.
Второй способ заключается в использовании регулярных выражений prxmatch
а также prxposn
найти и извлечь вложенное значение.
data have;
input;
longtext = _infile_;
datalines;
some thing #12.34, wicked
#, oops
#5a64, oops
# oops
oops ,
oops #
ok #1234,
who wants be a #1e6,aire
space # , the final frontier
double #12, jeopardy #34, alex
run;
data want;
set have;
* locate with index;
_p1 = index(longtext,'#');
if _p1 then _p2 = index(substr(longtext,_p1),',');
if _p2 > 2 then num_in_text = input (substr(longtext,_p1+1,_p2-2), ?? best.);
* locate with regular expression;
if _n_ = 1 then _rx = prxparse('/#(\d*\.?\d*)?,/'); retain _rx;
if prxmatch(_rx,longtext) then do;
call prxposn(_rx,1,_start,_length);
if _length > 0 then num_in_text_2 = input (substr(longtext,_start, _length), ?? best.);
end;
* drop _: ;
run;
Путь регулярного выражения ищет варианты ##.##, путь индекса ищет только #...,. Затем входная функция расшифрует значения научной нотации, которые регулярное выражение (пример шаблона) не найдет. ?? вариант в input
Функция предотвращает недопустимые аргументы. ПРИМЕЧАНИЕ:s в журнале, когда вложенное значение не может быть проанализировано как число.
Если вы хотите стать очень ленивым, вы можете просто сделать
want = compress(have,".","kd");