Подтвердить что ты не робот

Java "NoSuchMethodError"

Я получаю:

NoSuchMethodError: com.foo.SomeService.doSmth()Z

Я правильно понимаю, что этот 'Z' означает, что возвращаемый тип doSmth() является логическим? Если true, то такого метода действительно не существует, потому что этот метод возвращает некоторую коллекцию. Но, с другой стороны, если я вызываю этот метод, я не назначаю его возвращаемое значение для любой переменной. Я просто вызываю этот метод следующим образом:

service.doSmth();

Любые идеи, почему эта ошибка возникает? Все необходимые файлы JAR существуют, и все остальные методы из этого класса, похоже, существуют.

4b9b3361

Ответ 1

Похоже, что метод существует в пути к классам во время компиляции, но не во время запуска вашего приложения.

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

Ответ 2

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

Вкратце - файл класса /jar во время выполнения - это не то же самое, что вы использовали во время компиляции.

Ответ 3

Это, вероятно, разница между вашим пути времени компиляции и вашим путём класса времени выполнения.

Вот что происходит:

  • Код компилируется с помощью пути класса, который определяет метод doSmth(), возвращающий логическое значение. Байт-код относится к методу doSmth()Z.
  • Во время выполнения метод doSmth()Z не найден. Вместо этого найден метод, возвращающий коллекцию.

Чтобы исправить эту проблему, проверьте путь к классу (время компиляции).

Ответ 4

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

Если вы работаете, проверьте конфигурацию запуска Выберите вкладку "Выполнить" → "Выполнить конфигурации" → Выберите конфигурацию, в которой вы работаете, → "Проверить вкладку" Класс "- > Убедитесь, что библиотеки, которые вам нужны,

Если вы экспортируете (например, файл войны), выполните следующие действия: Выберите проект → Выбрать свойства → Выбрать сборку развертывания → Нажмите Добавить → Выбрать записи пути Java Build → Выберите библиотеки, которые вы хотите включить в экспортированный файл (например, военный файл)

В обоих случаях убедитесь, что библиотека, на которую вы ссылаетесь, включена.

Другими частыми проблемами для этой ошибки являются неправильный тип параметров или видимость, но затем компилятор обнаружит ошибку перед запуском. В этом случае просто проверьте документацию в соответствии с видимостью функции и пакета и убедитесь, что библиотека найдена в Java Build Path в ваших свойствах проекта.

Ответ 5

Я заметил эту проблему при тестировании некоторых экспериментальных изменений в нескольких связанных проектах после обновления их из SVN в Eclipse.

В частности, я обновил все проекты из SVN и вернул файл .classpath, а не редактировал его вручную, чтобы все было просто.

Затем я снова добавил связанные проекты к пути, но забыл удалить связанные банки. Так возникла проблема для меня.

Таким образом, очевидно, что время выполнения использовало файл jar, в то время как компилятор использовал файлы проекта.

Ответ 6

Может быть, все-таки может помочь кто-то, но это исключение может произойти и тогда, когда у вас есть на пути к классу два класса в разных файлах jar, которые имеют одинаковую точную подпись, но у них нет одинаковых общедоступных методов.

Например:

  • В файле mylibrary1.jar у вас есть класс com.mypackage.mysubpackage.MyClass с методом doSmth()

  • В файле mylibrary2.jar у вас есть класс com.mypackage.mysubpackage.MyClass без метода doSmth()

При поиске класса загрузчик классов может найти первый mylibrary2.jar в зависимости от приоритета пути, но не может найти метод в этом классе.

Убедитесь, что у вас нет одного класса пакетов + в двух разных файлах.

Ответ 7

Другим способом это может случиться и трудно найти:

Если подпись метода во внешней банке изменяется так, что в среде IDE отсутствует ошибка, поскольку она по-прежнему совместима с тем, как вы ее называете, класс не может быть повторно скомпилирован.

Если ваша сборка проверяет файлы на наличие изменений и только затем перекомпилирует их, класс не может быть перекомпилирован в процессе сборки.

Поэтому, когда вы его запускаете, это может привести к этой проблеме. Хотя у вас есть новая банка, ваш собственный код ожидает еще старого, но никогда не жалуется.

Чтобы сделать это сложнее, это зависит от jvm, если он может обрабатывать такие случаи. Так что в худшем случае он работает на тестовом сервере, но не на реальном компьютере.