Литмир - Электронная Библиотека

<Orders>

  <Order OrderId="99" OrderDateTime="01.02.2009">

    <Address>

      <Name>Владимир Иванов</Name>

      <Street>yn. CTpoMTanefr</Street>

      <House>12</House>

      <Apartment>23</Apartment>

      <City>MocKBa</City>

      <Zip>100888</Zip>

      <Country>Россия</Country>

    </Address>

  </Order>

  <Order OrderId="100" OrderDateTime="01.02.2009">

    <Address>

      <Name>Сергей Петров</Name>

      <Street>ул. Бажова</Street>

      <House>76</House>

      <Apartment>123</Apartment>

      <City>Eкатеринбург</City>

      <Zip>620000</Zip>

      <Country>Россия</Country>

    </Address>

  </Order>

</Orders>

Для получения имени по номеру ордера, используя LINQ для XML, мы можем написать следующий код:

XDocument xdoc =

XDocument.Load("D:\\CPS\\#Projects\\MVCBook\\MVCBook\\Order.xml");

IEnumerable<XElement> orders =

  xdoc.Element("Orders").Descendants("Order");

int orderId = 100;

IEnumerable<XElement> order =

  orders.Where(x => x.Attribute("OrderId").Value == orderId.ToString());

XElement address = order.Select(x => x.Element("Address"))

  .FirstOrDefault();

string name = address.Element("Name").Value;

В данном примере загружается файл orders.xml, в переменной orders присваиваются все заявки (элементы Order в XML-файле). Затем с помощью LINQ-запроса находится заявка с идентификатором 100. После этого выбирает элемент адреса заявки и, в завершение, из адреса извлекается имя.

Стоит отметить, что в данном примере не производились проверки возвращаемых значений на null, что на практике делать обязательно.

Работа с данными через ADO.NET

Понятие ADO.NET на платформе .NET достаточно широкое. На самом деле LINQ для SQL и LINQ для XML, а также все остальные стандартные LINQ-реализации входят в механизм ADO.NET как составные части. Но исторически ADO.NET развивалось от версии к версии платформы через другие механизмы, такие как объекты Dataset.

Dataset — это объект, содержащий кэш данных, загруженных из источника данных. По сути Dataset — это набор объектов типа DataTable, представляющих собой таблицы данных, и DataRelation, которые описывают связи между объектами DataTable.

Практически весь функционал по работе с данными через Dataset расположен в .NET Framework в пространствах имен System.Data и System.Data.OleDb (кроме этого, существует еще более двух десятков пространств имен, название которых начинается с System.Data). Перечислим основные самые важные классы, которые используются чаще всего при работе с Dataset из System.Data:

□ DataSet, DataTable, DataColumn, DataRow — различные варианты представления данных (набор, таблица, схема колонки, строка данных);

□ ConstraintCollection, Constraint, UniqueConstraint — представляют ограничения, которые могут быть наложены на объекты DataColumn.ConstraintCollection содержит набор таких ограничений для объекта DataTable;

□ DataView — объект, позволяющий привязывать данные из DataTable к формам WinForms или WebForms;

Список наиболее часто используемых классов пространства имен System.Data.OleDb:

□ OleDbConnection — обеспечивает подключение к базе данных через механизм OLE DB;

□ oleDbCommand — содержит запрос к базе данных на языке SQL либо представляет хранимую процедуру;

□ oleDataAdapter — обеспечивает заполнение объекта DataSet нужными данными с помощью элементов OieDbCommand;

□ oleDbDataReader — позволяет читать данные, полученные от oieDataAdapter, в виде строк и в прямом порядке;

□ oleDbTransaction — представляет собой транзакцию в источнике данных.

Существует еще одно часто используемое пространство имен, которое может быть полезно при разработке баз данных на SQL Server — System.Data.SqlClient. Это пространство имен содержит весь функционал System.Data.OleDb, только в реализации для использования исключительно с SQL Server. Применение этого пространства имен позволяет получить доступ к особенностям SQL Server, таким как новые типы данных SQL Server 2008.

Рассмотрим пример доступа к данным посредством базовых механизмов ADO.NET DataSet:

SqlConnection conn = new

  SqlConnection("Data Source=localhost,

      Initial Catalog=BookMVC, Integrated Security=True");

conn.Open();

SqlCommand cmd = new SqlCommand("SELECT * FROM Customers", conn);

SqlDataReader reader = cmd.ExecuteReader();

string phone;

while (reader.Read())

{

  string name = reader["name"].ToString();

  if (name == "Сергей Петров")

  {

    phone = reader["phone"].ToString();

    break;

  }

}

reader.Close();

conn.Close();

Данный пример инициализирует строку соединения с базой данных и открывает соединение. Затем создает команду в виде SQL-запроса на чтение всех записей из таблицы Customers (заказчики). С помощью ExecuteReader команда выполняется, и для работы с данными строится объект SqlDataReader. После этого формируется цикл, который проходит по всем записям, ищет первую запись с именем Сергей Петров и прерывает цикл, сохраняя данные о телефоне в локальной переменной.

Для сравнения перепишем этот простой пример, используя LINQ для Dataset:

SqlConnection conn = new SqlConnection(@"

Data Source=localhost;

Initial Catalog=BookMVC;

Integrated Security=True");

conn.Open();

SqlCommand cmd = new SqlCommand("SELECT * FROM Customers", conn);

DataSet ds = new DataSet();

SqlDataAdapter adapter = new SqlDataAdapter(cmd);

adapter.Fill(ds);

DataTable customers = ds.Tables[0];

string phone = customers. AsEnumerable()

  .Where(x => x.Field<string>("name") == "Сергей Петров")

  .Select(x => x.Field<string>("phone")).SingleOrDefault();

conn.Close();

Как нетрудно заметить, наш цикл, нацеленный на поиск данных, исчез, и ему на замену пришло LINQ-выражение, которое выполняет точно ту же логику — ищет телефон по определенному номеру.

Механизм доступа к данным через ADO.NET Dataset в общем случае производительнее, чем через ORM, вроде LINQ для SQL или Entity Framework, поскольку при работе с объектами типа Dataset нет затрат на реализацию объектной модели базы данных. Работа с данными происходит напрямую через SQL-запросы или вызов хранимых процедур. Разработчик сам контролирует весь процесс получения и использования данных, что дает больше возможностей и прирост производительности, но с другой стороны, увеличивает объем написания необходимого кода.

Поскольку основная часть времени при запросе тратится на его выполнение, то использование ADO.NET вместо популярных ORM для доступа к данным оправдано только там, где ставятся повышенные требования к потреблению памяти и производительности. В большинстве же случаев затраты на ORM окупаются скоростью и простотой разработки, единой моделью доступа к данным и меньшему количеству кода.

LINQ для SQL

16
{"b":"971383","o":1}