C # - инициализировать переменную, не зная, что это будет - PullRequest
4 голосов
/ 28 июня 2011

У меня есть две разные таблицы в моей базе данных, и каждая отображается пользователю на основе их "SortOrder". Я написал две функции, которые берут строку (или сущность) и меняют ее порядок сортировки на ближайшую к нему (вверх или вниз, в зависимости от того, какая функция выполняется). Мне нужно, чтобы эти функции работали для двух разных таблиц, в зависимости от того, где происходит событие (несколько видов сетки с одинаковой функциональностью). Вот что у меня есть (опять же, есть почти идентичная функция для перемещения вниз , но я не буду это публиковать, потому что это будет избыточно):

protected void moveUp(String ValId, String dbName)
    {
        int ValueId = Convert.ToInt32(ValId);
        DataModel.DataAccess.Entities dc = new DataModel.DataAccess.Entities();
        if (dbName.ToLower() == "table1")
        {
            DataModel.DataAccess.Table1 currentValue = dc.Table1.Single(table1item => table1item.Table1ItemId == ValueId);
        }
        else if (dbName.ToLower() == "table2")
        {
            DataModel.DataAccess.Table2 currentValue = dc.Table2.Single(table2item => table2item.Table2ItemId == ValueId);
        }
        try
        {
            //make the change and update the database and gridview
        }
        catch (InvalidOperationException)
        {
        }
    }

Очевидная проблема заключается в том, что мне нужно инициировать переменную currentValue перед операторами if, в противном случае существует "вероятность" того, что она никогда не будет объявлена, и поэтому функция (которая использует переменную currentValue) не будет работать.

У меня такой вопрос: как мне инициализировать переменную перед операторами if, если я еще не уверен, что это будет? Я думал, что это может сработать, но он говорит, что мне все еще нужно инициализировать его (« неявно типизированные локальные переменные должны быть инициализированы »):

    var currentValue; //this is the line where I get the error message above
    if (dbName.ToLower() == "table1")
    {
        currentValue = (DataModel.DataAccess.Table1)dc.Table1.Single(table1item => table1item.Table1ItemId == ValueId);
    }
    else if (dbName.ToLower() == "table2")
    {
        currentValue = (DataModel.DataAccess.Table2)dc.Table2.Single(table2item => table2item.Table2ItemId == ValueId);
    }

[РЕДАКТИРОВАТЬ] Изменено название, чтобы оно более точно отражало мой вопрос

Ответы [ 5 ]

7 голосов
/ 28 июня 2011

В C # все типы нуждаются в типе. Если ваши Table# типы расширяются DataModel.DataAccess.Table, используйте это:

DataModel.DataAccess.Table currentValue;

В противном случае вам нужно будет найти общий базовый класс (пра-пра-дедушка всех их объектов).

object currentValue;

Поскольку вы не инициализировали currentValue, компилятор не может знать, какой тип вы подразумеваете под var. Вот почему вы получаете исключение.

Приложение: Возможно, вместо ввода имени таблицы, вы можете использовать универсальный метод, такой как:

moveUp(dc.Table1, item => item.Table1Key, "george");

void moveUp<T> (IEnumerable<T> table, Func<T,string> keySelector, string ValId)
{
    T currentValue = table.Single(item => keySelector(item) == ValueId);

    try
    {
        //make the change and update the database and gridview
    }
    catch (InvalidOperationException)
    {
    }
}
2 голосов
/ 28 июня 2011

Вы можете попробовать написать интерфейс, который использует каждый объект, и функцию, которая принимает этот интерфейс.

public interface ISortableEntity
{
    int ID { get; set; }
    int SortOrder { get; set; }
}


 public class DataFunctions
{
    public static void MoveUp(string dbName, int valID)
    {
        var db = //Get your context here;
        List<KeyValuePair<string, object>> keys = new List<KeyValuePair<string, object>>();
        keys.Add(new KeyValuePair<string, object>("ID", valID));

        ISortableEntity entity = db.GetObjectByKey(new System.Data.EntityKey(dbName, keys)) as ISortableEntity;

        if (entity != null)
        {
            entity.SortOrder += 1;
        }

        db.SaveChanges();
    }
}
2 голосов
/ 28 июня 2011

Вместо var используйте объект типа, хотя я, вероятно, переписал бы весь этот процесс и использовал бы согласованные (и стандартные) соглашения об именах.

так:

object currentValue = null;
0 голосов
/ 28 июня 2011

Решение - интерфейсы.Ваши классы Table 1 и Table 2 должны реализовывать интерфейс (такой как ISortableTable или как вы хотите его называть) со свойством для CurrentValue.Реализация свойства CurrentValue в Table1 вернет правильный результат для Table1, а свойство CurrentValue в Table2 вернет правильный результат для Table2.Тогда ваша сортирующая функция может работать с любым классом, который реализует ISortableInterface, и работать со свойством CurrentValue соответствующего объекта.

0 голосов
/ 28 июня 2011

Вы не знаете тип переменной, поэтому вы объявляете ее неявно («var», а не, скажем, «int»)?

Вам не нужно инициализировать явные типы - неявные типы требуют этого, потому что они определяют свой тип по заданному значению.

...