Персонал / Страница сотрудника MySQL [дубликат]

Для небольших проектов вы правы. Я слышу ваш аргумент и сочувствую - однако есть веские причины для этой, тяжелой и повторяющейся работы, особенно в более крупных и более сложных приложениях:

  • Важно выполнить всю обработку в действии контроллера. Однако в примере, который вы указали, метод Repository.Get может возвращать lazily-оцененный объект IQueryable, что означало бы, что БД не пострадает, пока не будет оценен вид. По целому ряду причин это плохо. (Обходной путь состоит в том, чтобы вызвать .ToList, пока он все еще находится в контроллере).
  • «В представлении не должно быть никакой нерепрезентативной логики» и «Вы не должны доверять представлению» (поскольку представление может быть предоставленный пользователем). Предоставляя объект Model (потенциально все еще подключенный к активному DatabaseContext), представление может вносить вредоносные изменения в вашу базу данных.
  • Данные, отображаемые в представлении View, не всегда отображают 1: 1 с данными модели, например, рассмотрим страницу «Сведения о пользователе»: объект «Модель пользователя EF» представляет свою сущность в базе данных, поэтому он, вероятно, выглядит следующим образом: User { UserId, UserName, PasswordHash, PasswordSalt, EmailAddress, CreatedDate }, тогда как поля на странице «Сведения о пользователе» будут User { UserId, UserName, Password, ConfirmYourPassword, EmailAddress }, do вы видите разницу? Ergo, вы не можете использовать модель пользователя EF в качестве модели представления, вы должны использовать отдельный класс.
  • Опасности манипуляции с моделью: если вы разрешите ASP.NET MVC ( или любая другая инфраструктура) связывают модель с входящим HTTP POST-запросом (принимая приведенный выше пример сведений о пользователе), пользователь может сбросить пароль пользователя, присвоив значение свойства UserId. ASP.NET будет переписывать это значение во время привязки и, если вы специально не дезинформируете его (что будет так же тяжело, как создание отдельных ViewModels), тогда эта уязвимость останется.
  • В проектах с несколькими разработчиками, работающими в команде ситуация, , важно, чтобы все было согласовано . Не обязательно, чтобы на некоторых страницах использовались специальные модели ViewModels, но на других страницах, использующих модели EF, потому что команда не разделяет сознательный разум, все должно быть документировано и, как правило, имеет смысл. По той же причине один разработчик может уйти, не помещая чрезмерную документацию XML в свой исходный код, но в командной ситуации вы развалитесь, если вы этого не сделаете.

небольшое обходное решение в вашем случае Я поделюсь с вами, но учтите предварительные условия:

  • Ваши взгляды могут быть полностью доверены
  • Ваши взгляды содержат только презентационную логику
  • Ваше приложение в основном CRUD
  • Ваши представления соответствуют 1: 1 с каждой моделью сущности EF (т. е. нет JOIN)
  • . Ваши взгляды касаются только простых простых моделей для форм POST , а не сложные модели (т. е. объектный граф)

... тогда вы можете сделать это:

  • Поместить все односторонние, связанных с данными в вашу коллекцию ViewData, или ViewBag в MVC 4 (или даже общий ViewData<T>, если вы хардкор). Это полезно для хранения заголовков HTML-страниц и обмена данными с мастер-страницами.
  • Используйте ваши полностью оцененные и загруженные EF-модели в качестве моделей View<TModel>.

Но используйте этот подход с осторожностью, потому что он может ввести несогласованность.

97
задан Zbynek 18 September 2017 в 15:02
поделиться

3 ответа

MySQL имеет удобную функцию под названием FIELD() , которая отлично подходит для таких задач.

ORDER BY FIELD(Language,'ENU','JPN','DAN'), ID

Обратите внимание, что

  1. Это делает ваш SQL менее переносимым, поскольку другие СУБД могут не иметь такой функции
  2. Когда ваш список языков (или других значений для сортировки) становится намного дольше, лучше иметь отдельную таблицу с столбцом sortorder для них и присоединить ее к вашим запросам для заказа.
213
ответ дан Mchl 16 August 2018 в 10:38
поделиться
  • 1
    Спасибо, что это отлично для моей ситуации, когда мне просто нужно заказать два значения (основной язык, например JPN, и резервный язык, например, ENU). – Muleskinner 21 February 2012 в 16:11
  • 2
    Человек, которого вы только что спасли меня переписью в пурпуре :) – Erik Simonic 6 February 2015 в 16:18
  • 3
    Что, если у вас есть GROUP BY раньше? Например, первое значение, которое я хочу, появляется в конце? – Pathros 25 March 2015 в 19:51
  • 4
    Поместите запрос с GROUP BY в подзапрос и закажите его во внешнем запросе – Mchl 25 March 2015 в 21:55
  • 5
    Работа как шарм :) – raBne 19 June 2015 в 09:56

Если это единственные три значения, вы можете использовать a CASE выражение :

ORDER BY `ID`,
         CASE `Language`
         WHEN 'ENU' THEN 1
         WHEN 'JPN' THEN 2
         WHEN 'DAN' THEN 3
         END

(Если могут быть другие значения, тогда вы можете захотеть чтобы добавить некоторую дополнительную логику, чтобы упорядочить упорядочение, например, вы можете добавить ELSE 4 к этому выражению CASE, а затем упорядочить по Language в качестве третьего критерия заказа:

ORDER BY `ID`,
         CASE `Language`
         WHEN 'ENU' THEN 1
         WHEN 'JPN' THEN 2
         WHEN 'DAN' THEN 3
         ELSE 4
         END,
         `Language`
)
34
ответ дан Andrew Elliott 16 August 2018 в 10:38
поделиться
  • 1
    И если есть много значений языка, у вас может быть отдельная таблица, в которой хранятся каждый язык, а также столбец порядка сортировки и ссылка на этот – kaj 21 February 2012 в 15:45
  • 2
    Сначала он будет заказывать по идентификатору, что приведет к a, b, c, d, e, f – piotrm 21 February 2012 в 15:56
  • 3
    Спасибо, что работает отлично - как и Mchl ответ, который я принял, поскольку он выглядит проще – Muleskinner 21 February 2012 в 16:02
  • 4
    @piotrm: Ой, я бы неправильно понял вопрос. Благодарю. – ruakh 21 February 2012 в 16:03

У вас есть пара опций, прежде всего, чтобы изменить язык на ENUM (если это возможно, и вы ожидаете только нескольких вариантов)

Если вы укажете его как ENUM('ENU','JPN','DAN'), тогда ORDER Language ASC будет заказывать в указанном порядке.

Второй будет включать в себя случай где-то, т. е.

SELECT * FROM table
ORDER BY CASE Language
    WHEN 'ENU' THEN 3
    WHEN 'JPN' THEN 2
    WHEN 'DAN' THEN 1
    ELSE 0
END DESC, ID ASC

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

14
ответ дан Simon at mso.net 16 August 2018 в 10:38
поделиться
  • 1
    Где именно вы печатаете ENUM('ENU','JPN','DAN')? – Pathros 25 March 2015 в 19:52
  • 2
    @pathros в определении таблицы, вы указываете его как ENUM вместо VARCHAR и т. д. Внутри MySQL хранит опции ENUM в определенном порядке и индексирует их, поэтому при заказе столбцом ENUM он будет использовать этот внутренний индекс вместо строковые значения (если CAST () не используется для возврата к VARCHAR) – Simon at mso.net 26 March 2015 в 10:36
  • 3
    Должно ли END DESC, быть END CASE DESC,? – Istiaque Ahmed 10 November 2017 в 15:11
  • 4
    Неа. Не все CASE нуждаются END CASE, это зависит от контекста. CASE в рамках ПРОЦЕДУРЫ требуют END CASE ( dev.mysql.com/doc/refman/5.5/en/case.html ), однако CASE в SELECT не требует END CASE, просто END ( dev.mysql.com/doc/refman/5.7/en/… ) - в этом контексте это функция потока управления. – Simon at mso.net 10 November 2017 в 19:33
Другие вопросы по тегам:

Похожие вопросы: