2014-10-31 2 views
0

Я хотел бы проверить введенную строку в запятой, что довольно просто (просто используется: How can I check if a single character appears in a string?). Теперь я хочу проверить, присутствует ли персонаж более одного раза. (В этом случае запятая (/ u002C)) Я создал этот код:Java: проверьте, содержит ли строка более одного символа

public static void addTextLimiterDouble(final TextField tf, final int maxLength, final Button submitButton) { 
    tf.textProperty().addListener(new ChangeListener<String>() { 
     @Override 
     public void changed(final ObservableValue<? extends String> ov, final String oldValue, final String newValue) { 

      if (oldValue.contains("\u002C") && newValue.endsWith("\u002C")) { 
       tf.setText(oldValue); 
      } 
    } 
}); 

Это дает ошибку StackOverflow, потому что кажется, она не может выйти из цикла. Может ли кто-нибудь объяснить, почему это невозможно?

Примечание: Я знаю, что есть несколько способов проверить наличие нескольких персонажей, но мне просто интересно, почему это дает мне ошибку.

Любая помощь очень ценится!

ответ

2

Представьте ситуацию (на самом деле, это, скорее всего, ситуация, в которой вы находитесь), где вы редактируете строку, которая заканчивается в запятой. Когда вы меняете что-то еще в этой строке, то ваше if заявления (if (oldValue.contains("\u002C") && newValue.endsWith("\u002C"))) возвращает true и вы пытаетесь вернуться к старому значению по телефону tf.setText()

However-, что изменения в тексте! И ваш ChangeListener вызывается снова. Новое значение заканчивается запятой (вы возвращались обратно к значению, которое заканчивается запятой), а старое значение также содержит запятую, поэтому снова ваш слушатель вызывает tf.setText().

После этого он вызывает ваш ChangeListener, потому что текст был изменен. И снова ... ad nauseum

+0

Спасибо за это замечательное объяснение! Я думал, что ChangeListener будет вызван только пользователем, чередующим текст в текстовом поле, но это, очевидно, не так. – bashoogzaad

1

String.endsWith проверяет, существует ли переданный String в конце String, вызывающий метод, но это не то, что вы готовы сделать.

Это то, что я хотел бы сделать:

int index = myString.indexOf(ch); 
boolean moreThanOnce = index != -1 && index != myString.lastIndexOf(ch); 

Однако ваш тест кажется странным для меня, так как он испытывает что-то на обоих oldValue и newValue. Если бы я хорошо понял, что вы хотите сделать, вы должны рассмотреть только один из этих двух.

+0

Благодарим вас за это объяснение и за вашу альтернативу для этого. Он отлично работает! – bashoogzaad

1

Вы добавляете прослушиватель в свой текстовый фильтр. Затем вы переопределяете метод changed(). В этом методе вы вызываете setText() !! Это снова вызовет Listeners changed() .... так что вы попадаете в бесконечный цикл ...