Отображение данных через linq - PullRequest
0 голосов
/ 14 апреля 2019

Я хочу отобразить информацию о еде для определенных рейтингов.

List<Rating> rates = db.Ratings.OrderByDescending(e => e.Rate).ToList();                    
int i = 0;
foreach(Rating rate in rates)
{
    rates[i].Food = db.Foods.Where(e => e.ID == rate.FID).FirstOrDefault();
    i++;
}
return Request.HttpCreateResponse(rates);

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

"rate": [
        {
            "ID": 15,
            "Rate": 5,
            "FID": 65,
            "UID": 102,
            "Food": {
                "ID": 65,
                "Name": "Grilled chicken",
                "Price": "580",
                "CatID": 75,
                "UID": 101,
                "Date_Time": "2019-04-01T00:00:00",
                "FoodDescription": "Chicken with some oregeno",
                "CookingTime": "25 min",
                "Image": "",
                "Uploadedby": "Hanzala Iqbal",
                "Carts": [],
                "Category": null,
                "User": null,
                "FoodRecommendations": [],
                "OrderFoods": [],
                "Ratings": []
            },

Я хочувот так.

{
    "ID": 65,
    "Name": "Grilled chicken",
    "Price": "580",
    "CatID": 75,
    "UID": 101,
    "Date_Time": "2019-04-01T00:00:00",
    "FoodDescription": "Chicken with some oregeno",
    "CookingTime": "25 min",
    "Image": "",
    "Uploadedby": "Hanzala Iqbal",
    "Carts": [],
    "Category": null,
    "User": null,
    "FoodRecommendations": [],
    "OrderFoods": [],
    "Ratings": []
},

Надеюсь, вы понимаете, чего я пытаюсь добиться Заранее спасибо.

1 Ответ

1 голос
/ 15 апреля 2019

Основываясь на rates[i].Food = ..., ваша сущность Rating уже имеет отношение, установленное для Food.Ваш код выполняет несколько ненужных вещей:

  1. Выберите N + 1: перебирая уже полученные рейтинги, вы снова отправляетесь в базу данных, чтобы получить еду.Это означает, что 1 запрос для чтения 200 оценок и 200 запросов для считывания пищи 1 за один раз.
  2. Установка ссылки на сущность, когда вы не хотите обновлять сущности: это плохая практика, потому что, если позже код вобласть действия этого DbContext вызывает SaveChanges, в которых у вас будут ошибки FK или данные, которые вы не собираетесь обновлять.
  3. Возврат сущностей и неправильная сущность: вы не хотите возвращать рейтинги, вы хотитевернуть еду.Вам также следует избегать возврата объектов Entity из вызовов, потому что это часто включает в себя слишком много информации о вашей схеме, и вы должны никогда принимать объекты из клиентского кода, чтобы сделать что-то вроде присоединения к контексту и SaveChanges.Это удобно и требует меньше кодирования, но подвергает вашу систему неожиданным / непреднамеренным обновлениям.

Чтобы получить то, что вы хотите, вам просто нужно использовать соотношение между рейтингами и едой, выберитерелевантные данные в ViewModel и вернуть модель представления.

ViewModel:

[Serializable]
public class FoodViewModel
{
    public int ID {get; set}
    public string Name {get; set}
    public decimal Price {get; set}
    public DateTime Date_Time" {get; set}
    public string FoodDescription {get; set}
    public string CookingTime {get; set}
    public string Uploadedby {get; set}
}

Если вам нужно вернуть наборы данных (корзины, FoodRecommendations и т. д.), тогда определите модели представления дляэти.Как правило, просто возвращайте данные, которые нужны вашему мнению / потребителю.

Чтобы выбрать продукт по убыванию рейтинга:

var foodViewModels = db.Ratings.OrderByDescending(e => e.Rate)
    .Select(e => new FoodViewModel
    {
        ID = e.Food.ID,
        Name = e.Food.Name,
        Price = e.Food.Price,
        DateTime Date_Time = e.Food.Date_Time,
        FoodDescription = e.Food.FoodDescription,
        CookingTime = e.Food.CookingTime,
        UploadedBy = e.Food.UploadedBy
    }).Distinct().ToList();

return Request.HttpCreateResponse(foodViewModels);

Как и предполагалось, соотношение между продуктами питания и рейтингами выглядит какмногие-к-одному, где каждый продукт может иметь более одного рейтинга, поэтому вам, вероятно, придется ограничить результаты, чтобы список продуктов был только по максимальному рейтингу.A .Distinct() может быть достаточно до .ToList(), либо этого, либо выберите из db.Foods и упорядочите по .Max(f => Rating.Rate)

Т.е.:

var foodViewModels = db.Foods.OrderByDescending(f => f.Ratings.Max(r => r.Rate))
    .Select(f => new FoodViewModel
    {
        ID = f.ID,
        Name = f.Name,
        Price = f.Price,
        DateTime Date_Time = f.Date_Time,
        FoodDescription = f.FoodDescription,
        CookingTime = f.CookingTime,
        UploadedBy = f.UploadedBy
    }).ToList();
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...