Не удается преобразовать проблемы с преобразованием типов, не допускающих значение NULL, vb.net в С#

Я скопировал фрагмент устаревшего кода, написанного на VB.Net, который при преобразовании в C# дал следующее:

///<summary>
    ///Test whether SSAC should be serialized
    ///</summary>
    public virtual bool ShouldSerializeSSAC()
    {
        if (_shouldSerializeSSAC)
        {
            return true;
        }
        return (_sSAC != (SSAC_Type)null);
    }

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

[System.CodeDom.Compiler.GeneratedCodeAttribute("System.Xml", "4.6.81.0"), System.SerializableAttribute()]
public enum SSAC_Type
{

    ///<remarks/>
    A,

    ///<remarks/>
    B,

    ///<remarks/>
    C,

    ///<remarks/>
    D,

    ///<remarks/>
    E,

    ///<remarks/>
    F,

    ///<remarks/>
    G,

    ///<remarks/>
    H,

    ///<remarks/>
    J
}

В VB.Net эта функция выглядела следующим образом:

Public Overridable Function ShouldSerializeSSAC() As Boolean
        If _shouldSerializeSSAC Then
            Return True
        End If
        Return (_sSAC <> CType(Nothing, SSAC_Type))
    End Function

В то время как класс SSAC был следующим:

 <System.CodeDom.Compiler.GeneratedCodeAttribute("System.Xml", "4.6.81.0"),
 System.SerializableAttribute()>
Public Enum SSAC_Type

    '''<remarks/>
    A

    '''<remarks/>
    B

    '''<remarks/>
    C

    '''<remarks/>
    D

    '''<remarks/>
    E

    '''<remarks/>
    F

    '''<remarks/>
    G

    '''<remarks/>
    H

    '''<remarks/>
    J
End Enum

Как я могу обновить код C#, чтобы исправить эту ошибку?


person Jay    schedule 10.04.2016    source источник


Ответы (2)


Ну, «исправить», возможно, не лучший термин для использования здесь, так как это, вероятно, было непреднамеренным поведением в коде VB. Но если под «исправлением» вы подразумеваете, как заставить его работать так же, тогда ответ заключается в том, что код C# должен возвращать (_sSAC != SSAC_Type.A). Чтобы исправить это, _sSAC следует объявить как SSAC_Type? (nullable), тогда вы можете просто вернуть _sSAC.HasValue. Причина, по которой это работало в VB, заключается в том, что Nothing в VB не совсем эквивалентно null в C#. Nothing на самом деле означает значение по умолчанию для любого заданного типа, поэтому для целого числа, такого как перечисление, значение по умолчанию равно 0.

person Steven Doggart    schedule 10.04.2016
comment
Означает ли это, что return (_sSAC != (SSAC_Type)null); всегда возвращает первый объект в списке перечислений? - person Jay; 10.04.2016
comment
Нет. Он возвращает логическое значение. Возвращает true, если _ssac не равно A (0). - person Steven Doggart; 10.04.2016
comment
OK Я вижу, где я могу установить SSAC_Type? как обнуляемый, что вы имеете в виду в отношении возврата _sSAC.HasValue? Я не вижу метод HasValue, только HasFlag - person Jay; 10.04.2016
comment
Я просто предполагаю, что это было то, что код безуспешно намеревался сделать. - person Steven Doggart; 10.04.2016
comment
Я думаю, что вопрос, который вам нужно решить, заключается в том, что VB пытался сделать и чего вы от него хотите. Это полная ерунда, как написано. Таким образом, вам нужно решить, следует ли сверяться с нулевым значением или переписать все это так, чтобы _sSac имел значение Nullable. Вопрос не столько в переводе, сколько в том, чтобы решить, что вам нужно, и соответственно написать. - person Stuart Whitehouse; 10.04.2016
comment
@StuartWhitehouse Спасибо, что объяснили это лучше, чем я. Я был за рулем, поэтому я не мог ответить более подробно. - person Steven Doggart; 11.04.2016

«Ничто» при применении к экземпляру перечисления всегда равно «0» в VB, независимо от того, установлено ли явно первое значение перечисления на что-либо еще. То есть фактическое первое значение перечисления не имеет значения. Таким образом, С# эквивалентен вашему методу:

public virtual bool ShouldSerializeSSAC()
{
    if (_shouldSerializeSSAC)
        return true;

    return (_sSAC != 0);
}
person Dave Doknjas    schedule 10.04.2016
comment
спасибо, Дэйв, я решил изменить переменные на nullable и вернуть _sSAC.HasValue - person Jay; 10.04.2016