2009-02-01 4 views
0

Я должен заменить содержимое этой XML-строки через Javaзамена регулярных выражений в Java строку, которая содержит ` ` символ

<My:tag>value_1 22&#xA;value_2 54&#xA;value_3 11</My:tag> 

так, эта строка была взята из XML, и когда я приобрести это я иметь этот результат:

<My:tag>value_1 22 
value_2 54 
value_3 11</My:tag> 

Если я пытаюсь заменить содержимое по этому пути:

String regex = "(<My:tag>)(.*)(</My:tag>)"; 
String new_string = old_string.replaceAll(regex,"<My:tag> new_stuff </My:tag>"); 

Я не получаю никакого результата. Я думаю, из-за &#xA; символ

, но если я попытаюсь заменить строку без символа &#xA;, все будет хорошо.

Предложения? Thanks

+0

Giancarlo: Я рекомендую использовать тег 'regex' вместо' регулярных выражений', так как он намного более популярен (и, следовательно, больше людей будут определять ваши вопросы). Поскольку существует ограничение на 5 тегов, а xA не является определенным термином, который люди будут искать, я заменил этот тег на 'regex'. –

ответ

1

Я не уверен на 100%, как работает механизм регулярного выражения java, но я не могу себе представить, что сущность вызовет ваши проблемы. Сначала вы должны просто удалить свои скобки, поскольку вы заменяете все выражение и не извлекаете ничего.

Что может быть причиной этого, если ваша сущность фактически переводится на новую строку, может быть, что ваше регулярное выражение не сможет его поймать, если вы явно не выполняете многострочное совпадение. Кроме того, можно попробовать сделать

[.\n]* 

вместо вашего

.* 

Это может быть предложение жадного, хотя, и возвраты много для сличитель обрабатывать. К сожалению, у меня нет никаких java-файлов, установленных на этой машине, поэтому я не могу попробовать и протестировать их. Еще одна возможность заключается в том, чтобы активно искать следующий угол открытия кронштейн, например, так:

[^<]* 

EDIT:
Как вы предложили, я попробовал вашу ссылку и на следующий работал отлично:

Expression :

<My:tag>[^<]*</My:tag> 

Замена:

<My:tag> new_stuff </My:tag> 

Тест строка:

<My:tag>value_1 22&#xA;value_2 54&#xA;value_3 11</My:tag> 
+0

это не работает, однако я не использую никакой дополнительной библиотеки. Если вы хотите, вы можете сделать какой-то эксперимент здесь http://www.fileformat.info/tool/regex.htm – Giancarlo

+0

Java имеет флаг (? S) для режима DOTALL - включение. соответствует новой строке. Действительно [.] Будет соответствовать фактическому. не любой символ. Кроме того, [^>] * будет работать так, как ожидалось, и не сталкивается с окончанием слова. –

+0

очень хорошо, это работает [^>] * :) Большое спасибо – Giancarlo

0

Я бы предложил использовать библиотеку XML, такую ​​как JDOM или DOM4J, для управления XML вместо использования регулярных выражений.

+0

JDOM и DOM4J кажутся излишними, если вам просто нужно немного манипулировать текстом. Вы правы, если вам нужно делать крупномасштабные вещи, но для этого ... нет. – falstro

+0

точно, мне нужно только манипулировать такими строками, я не думаю, что это имеет смысл использовать другую библиотеку ... – Giancarlo

+0

Еще одно преимущество использования библиотеки XML заключается в том, что результат ваших манипуляций гарантированно будет правильно сформированным XML - В чем смысл (извините?) XML, не так ли? –

1

Я не могу понять, почему сам &#xA; вызовет какой-либо вопрос - не, если она становится преобразуется в фактической символ новой строки в какой-то момент.

Если это так, вам нужно включить режим DOTALL, чтобы. также совпадает с новой строкой (что не по умолчанию).

Чтобы включить DOTALL, просто запустите выражение с (?s)
(., Если вы создали объект Pattern, вы можете также передать флаг, чтобы это)

Во всяком случае, попробуйте следующее:

String regex = "(?s)(?<=<(My:tag)>).*?(?=</\1>)"; 
String new_string = old_string.replaceAll(regex,"new_stuff"); 


Вы также можете включить его для определенной части регулярного выражения с (?s:регулярного выражения сегмента), например:

String regex = "(?<=<(My:tag)>)(?s:.*?)(?=</\1>)"; 
+0

Да, если описание проблемы является точным, сущности должны заменяться линейными переводами до того, как будет применено регулярное выражение. Кроме того, вы должны были использовать не-жадную точку-звезду (. *?), Но это еще более важно, когда вы выполняете матч в режиме DOTALL. –

+0

Это немного двусмысленно; я имел в виду, что GIANCARLO должен был использовать не-жадную точку-звезду, как это сделал Питер. –

Смежные вопросы