Невозможно создать постоянное значение типа (type). В этом контексте поддерживаются только примитивные типы (такие как Int32, String и Guid). - PullRequest
11 голосов
/ 28 августа 2011

Я прочитал ВСЕ о:

и искал немного больше, но все еще не нашел решения. Я видел, что это происходит на EF 3.5, а в 4.0 должен поддерживаться метод Contains, но я нахожусь в EF 4, но я получаю эту ошибку. У меня есть фотогалерея, где в альбомах может быть любое количество разных фотографий, и каждая фотография может принадлежать к любому количеству альбомов. Так что это отношения многие ко многим.

У меня есть свойство VisibleObjects, которое используется около 100 другими методами, которые работают хорошо, но я все равно вставляю его: (Я точно уверен, что проблема не , вызванная что-то здесь)

static IQueryable<GlobalObject> VisibleObjects
    {
        get
        {
            return from obj in db.GlobalObjectSet where obj.IsVisible && !obj.SiteUser.IsDeactivated orderby obj.ID descending select obj;
        }
    }

Я пробовал несколько разных запросов:

У меня есть VisiblePhotos свойство:

Это не сработало:

static IQueryable<Photo> VisiblePhotos(this Album a)
    {
        return from p in VisibleObjects.OfType<Photo>() where a.Photos.Contains(p) select p;
    }

Изменено на это:

static IQueryable<Photo> VisiblePhotos(this Album a)
    {
        return from p in VisibleObjects.OfType<Photo>() where a.Photos.Any(other => p.ID == other.ID) select p;
    }

Все еще не работал.

Вот метод вызова:

public static List<Photo> GetLatestPhotosByAlbum(Album alb, int count = 3)
    {
        lock (sync)
        {
            return alb.VisiblePhotos().OrderByDescending(p => p.ID).Take(count).ToList();
        }
    }

Не работал, изменился на:

public static List<Photo> GetLatestPhotosByAlbum(Album alb, int count = 3)
    {
        lock (sync)
        {
            return (from p in VisibleObjects.OfType<Photo>()
                    where alb.Photos.Any(ph => ph.ID == ph.ID)
                    select p).ToList();
        }
    }

Все еще не работает. Жалуется на невозможность создать константу моего типа объекта Photo, который является объектом Entity со свойством ID, если это помогает. Я не уверен в истинной причине ошибки, и у меня нет других идей о запросах. Я думаю, что название метода самоочевидно: я пытаюсь получить фотографии в данном альбоме. Загрузка записей альбома в память не является решением, запрос должен выполняться по базе данных, а не по памяти. Мне нужно объяснение этого исключения, , почему это происходит здесь, и как я могу заставить мой запрос работать.

Ответы [ 4 ]

12 голосов
/ 28 августа 2011

Это не будет работать, потому что вы хотите использовать локальный альбом в запросе linq-to-entity.Вы должны либо использовать свойство навигации на p, чтобы получить его альбом:

var query = from p in VisibleObjects.OfType<Photo>()
            where p.Album.Id == alb.Id
            select p;

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

5 голосов
/ 28 августа 2011

Я думаю, что EF пытается преобразовать where a.Photos.Contains(p) в SQL как WHERE p IN (a.Photos), но не знает, как выразить a.Photos в SQL.Требуемый SQL, вероятно, выглядит как WHERE p.Id IN (1, 2, 3), поэтому вы можете попробовать сделать это в C #:

static IQueryable<Photo> VisiblePhotos(this Album a)
{
    var photoIds = a.Photos.Select(p => p.Id).ToArray();
    return from p in VisibleObjects.OfType<Photo>() where photoIds.Contains(p.Id) select p;
}
0 голосов
/ 18 июля 2012

Я столкнулся с подобной проблемой, и вместо IQueryable я попытался использовать List, и это сработало. Может быть какая-то помощь.

0 голосов
/ 28 августа 2011

Я попробовал другой способ, и это сработало:

static IQueryable<Photo> VisiblePhotos(this Album a)
{
    return from p in VisibleObjects.OfType<Photo>()
           where p.Albums.Any(alb => a.ID == alb.ID)
           select p;
}

Довольно странно видеть, что это работает, но другой нет. Но мне все еще интересно, почему Contains не работает.

...