Игнорировать исключение NullReferenceException при чтении свойств объекта - PullRequest
5 голосов
/ 18 ноября 2008

Есть ли способ заставить C # игнорировать NullReferenceException (или любое конкретное исключение в этом отношении) для набора операторов. Это полезно при попытке прочитать свойства десериализованного объекта, который может содержать много нулевых объектов. Наличие вспомогательного метода для проверки на null может быть одним из способов, но я ищу что-то похожее на «On Error Resume Next» (из VB) на уровне блока операторов.

РЕДАКТИРОВАТЬ: Try-Catch пропустит последующие операторы при исключении

try
{
   stmt 1;// NullReferenceException here, will jump to catch - skipping stmt2 and stmt 3
   stmt 2;
   stmt 3;
}
catch (NullReferenceException) { }

Например: я десериализирую сообщение XML для объекта, а затем пытаюсь получить доступ к свойству типа

Message.instance[0].prop1.prop2.ID

теперь prop2 может быть нулевым объектом (потому что он не существует в XML Message - необязательный элемент в XSD). Прямо сейчас мне нужно проверить нулевое значение для каждого элемента в иерархии, прежде чем получить доступ к элементу листа. то есть я должен проверить, если instance [0], prop1, prop2 не равны NULL, прежде чем получить доступ к «ID».

Есть ли лучший способ избежать проверки на нуль для каждого элемента в иерархии?

Ответы [ 5 ]

6 голосов
/ 18 ноября 2008

Короче говоря: нет. Проверьте нулевую ссылку, прежде чем пытаться ее использовать. Одним из полезных приемов здесь могут быть методы расширения C # 3.0 ... они позволяют показывать вызывать что-либо по нулевой ссылке без ошибок:

string foo = null;
foo.Spooky();
...
public static void Spooky(this string bar) {
    Console.WriteLine("boo!");
}

Кроме этого - возможно, какое-то использование условного оператора?

string name = obj == null ? "" : obj.Name;
4 голосов
/ 18 ноября 2008

троичный оператор и / или ?? Оператор может быть полезным.

Скажем, вы пытаетесь получить значение myItem.MyProperty.GetValue (), и MyProperty может быть нулевым, и вы хотите установить пустую строку по умолчанию:

string str = myItem.MyProperty == null ? "" : myItem.MyProperty.GetValue();

Или в случае, когда возвращаемое значение GetValue равно нулю, но вы хотите установить значение по умолчанию:

string str = myItem.MyProperty.GetValue() ?? "<Unknown>";

Это может быть объединено с:

string str = myItem.MyProperty == null 
    ? "" 
    : (myItem.MyProperty.GetValue()  ?? "<Unknown>");
1 голос
/ 14 декабря 2008

теперь я использую делегат и обработку NullReferenceException

public delegate string SD();//declare before class definition

string X = GetValue(() => Message.instance[0].prop1.prop2.ID); //usage

//GetValue defintion
private string GetValue(SD d){
        try
        {
            return d();
        }
        catch (NullReferenceException) {
            return "";
        }

    }

Благодаря Try-catch для каждой строки кода без отдельных блоков try-catch за идею

0 голосов
/ 18 ноября 2008

Я бы пошел с помощью вспомогательного метода. При ошибке Resume Next просто приводит к безумию.

0 голосов
/ 18 ноября 2008
try
{
   // exceptions thrown here...
}
catch (NullReferenceException) { }
...