Ограничение универсального кода вещами, которые могут иметь значение NULL

При генерации XML-файлов программно можно хотеть посмотреть библиотека XMLBeans . Используя инструмент командной строки, XMLBeans автоматически генерирует и пакет ряд объектов Java на основе XSD. Можно затем использовать эти объекты создать XML-документ на основе этой схемы.

Это имеет встроенную поддержку проверки схемы и может преобразовать объекты Java в XML-документ и наоборот.

Castor и JAXB является другими библиотеками Java, которые служат подобной цели к XMLBeans.

23
задан joce 13 January 2014 в 01:24
поделиться

2 ответа

Нет, нет способа сделать это во время компиляции.

Лично я бы просто позволил T быть чем-нибудь, а затем проверил бы его валидность в статическом конструкторе:

public class MyGeneric<T>
{
    static MyGeneric()
    {
        var def = default(T); 
        if (def is ValueType && Nullable.GetUnderlyingType(typeof(T)) == null)
        {
            throw new InvalidOperationException(
                string.Format("Cannot instantiate with non-nullable type: {0}",
                    typeof(T)));
        }
    }
}
12
ответ дан 29 November 2019 в 03:06
поделиться

Иногда система типов просто не может делать то, что вы хотите. В этих случаях вы либо меняете то, что хотите, либо работаете над этим.

Рассмотрим пример класса Tuple<>. «Самая большая» версия выглядит как Tuple<T1, T2, T3, T4, T5, T6, T7, TRest>, где TRest должно быть Tuple<>. Это не ограничение времени компиляции, это строго проверка во время выполнения. Возможно, вам придется прибегнуть к чему-то похожему, если вы хотите применить требование обнуления из T в Foo<T>, поддерживающее как типичные классы, так и обнуляемые структуры.

/// <summary>
/// Class Foo requires T to be type that can be null. E.g., a class or a Nullable&lt;T&gt;
/// </summary>
/// <typeparam name="T"></typeparam>
class Foo<T>
{
    public Foo()
    {
        if (default(T) != null)
            throw new InvalidOperationException(string.Format("Type {0} is not valid", typeof(T)));
    }

    // other members here
}

Выполняя это, я документирую, что класс потребует, чтобы T был совместим с обнуляемыми типами и добавлял конструктор, если это не так.

Foo<string> foo = new Foo<string>(); // OK
Foo<int?> works = new Foo<int?>(); // also OK
Foo<int> broken = new Foo<int>(); // not OK
0
ответ дан 29 November 2019 в 03:06
поделиться
Другие вопросы по тегам:

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