Как я ловлю ClassCastException?

  1. Установите ansible в свой virtualenv или иным образом сделайте так, чтобы PyCharm мог видеть файл ansible в bin; К сожалению, поскольку у них 164 строки Python вместо просто __main__, вы не можете вызывать его как python -m ansible.cli.playbook или любая такая тонкость
  2. создает конфигурацию запуска с «Python Script» указывая на .../bin/ansible или .../bin/ansible-playbook и т. д.

    Для вашего удобства вы также можете открыть bin/ansible в PyCharm, перейти к строке if __name__ и нажать «треугольник игры» в левом желобе. , хотя это приведет к запуску процесса python в каталоге bin, что может раздражать

  3. установить точку останова в выбранном вами файле ansible
  4. запустите отладчик

Имейте в виду, что в группе дел ANSIBLE собирается выложить что-то для выполнения, и, насколько мне известно, отладчик PyCharm не следует за подпроцессом или его друзей, так что вам придется перепрыгивать через некоторые обручи, если вы хотите иметь возможность отлаживать модули этого стиля, включая любой из ваших собственных сценариев в library/*.py или что-то еще.

Я очень люблю PyCharm, но в этом конкретном случае вы можете быть более счастливы, используя strategy: debug в своей книге игр и сражаясь с отладчиком ansible

8
задан Hooked 6 March 2015 в 04:40
поделиться

4 ответа

Код в вопросе должен дать Вам предупреждение броска непроверенное. Слушайте-Xlint.

Весь компилятор знает о T, его границы, которые он, вероятно, не имеет (кроме явно расширяющегося Объекта и супер из пустого типа). Таким образом, эффективно бросок во времени выполнения (Объект) - не очень полезен.

То, что можно сделать, передать в экземпляре Класса параметризованного типа (предполагающий, что это не универсально).

class MyReader<T> {
    private final Class<T> clazz;
    MyReader(Class<T> clazz) {
        if (clazz == null) {
            throw new NullPointerException();
        }
        this.clazz = clazz;
    }
    public T restore(String from) {
        ...
        try {
            restoredItem = clazz.cast(decoder.readObject());
            ...
            return restoredItem;
        } catch (ClassCastException exc) {
            ...
        }
    }
}

Или как общий метод:

    public <T> T restore(Class<T> clazz, String from) {
        ...
        try {
            restoredItem = clazz.cast(decoder.readObject());
            ...
11
ответ дан 5 December 2019 в 12:14
поделиться

Не будет никакого ClassCastException, кроме тех случаев, когда Ваш T имеет некоторую основу:

public class GenericsTest
{
    public static void main(String[] args)
    {
        System.out.println(cast(Integer.valueOf(0)));
        System.out.println(GenericsTest.<Long> cast(Integer.valueOf(0)));
        System.out.println(GenericsTest.<Long> cast("Hallo"));

        System.out.println(castBaseNumber(Integer.valueOf(0)));
        System.out.println(GenericsTest.<Long> castBaseNumber(Integer.valueOf(0)));
        System.out.println(GenericsTest.<Long> castBaseNumber("Hallo"));
    }

    private static <T extends Number> T castBaseNumber(Object o)
    {
        T t = (T)o;
        return t;
    }

    private static <T> T cast(Object o)
    {
        T t = (T)o;
        return t;
    }
}

В вышеупомянутом примере не будет никакого ClassCastException в первых 5 вызовах, которые бросят и castBaseNumber. Только 6-й вызов бросает ClassCastException, потому что компилятор эффективно переводит бросок () для возврата (Объект) o и castBaseNumber () для возврата (Номер) o;. Wenn Вы пишете

String s = GenericsTest.<Long> cast("Hallo");

Вы получили бы ClassCastException, но не в рамках метода броска, а в присвоении на s.

Поэтому я думаю, Ваш "T" не просто "T", но и "T расширяет Что-то". Таким образом, Вы могли проверить:

Object o = decoder.readObject();
if (o instanceof Something)
    restoredItem = (T) o;
else 
    // Error handling

Но это все еще приведет к ошибке позже, когда Вы будут использовать Ваш класс.

public Reader<T extends Number>{...}

Long l = new Reader<Long>("file.xml").getValue(); // there might be the ClassCastException

Для этого случая только советует Tom, мог бы помочь.

3
ответ дан 5 December 2019 в 12:14
поделиться

Ну, я не могу использовать instanceof оператор как метод является параметрическим:

public T restore(String from){
...
restoredItem = (T) decoder.readObject();
...
}

И дженерики в Java являются временем компиляции только.

0
ответ дан 5 December 2019 в 12:14
поделиться

Если Вы не можете использовать instaceof, Вы смогли использовать isAssignableFrom метод на Классе

0
ответ дан 5 December 2019 в 12:14
поделиться
Другие вопросы по тегам:

Похожие вопросы: