Платформа DevExpress eXpressApp Framework (XAF) и Экспресс-постоянные объекты (XPO):как мне ускорить время загрузки ассоциаций?
-
09-06-2019 - |
Вопрос
У меня возникла проблема со скоростью доступа к свойству ассоциации с большим количеством записей.
У меня есть приложение XAF с родительским классом под названием MyParent
.
В нем насчитывается 230 записей MyParent
.
MyParent
имеет дочерний класс под названием MyChild
.
В нем насчитывается 49 000 записей MyChild
.
У меня есть ассоциация, определенная между MyParent
и MyChild
стандартным способом:
В MyChild
:
// MyChild (many) and MyParent (one)
[Association("MyChild-MyParent")]
public MyParent MyParent;
И в MyParent
:
[Association("MyChild-MyParent", typeof(MyChild))]
public XPCollection<MyCHild> MyCHildren
{
get { return GetCollection<MyCHild>("MyCHildren"); }
}
Есть определенный MyParent
вызванная запись MyParent1
.
Для MyParent1
, всего насчитывается 630 MyChild
записи.
У меня есть DetailView для класса под названием MyUI
.
Пользователь выбирает элемент в одном раскрывающемся списке в MyUI
DetailView, и мой код должен заполнить другой выпадающий список MyChild
Объекты.
Пользователь выбирает MyParent1
в первом выпадающем списке.
Я создал свойство в MyUI
чтобы вернуть коллекцию MyChild
объекты для выбранного значения в первом раскрывающемся списке.
Вот код для этого свойства:
[NonPersistent]
public XPCollection<MyChild> DisplayedValues
{
get
{
Session theSession;
MyParent theParentValue;
XPCollection<MyCHild> theChildren;
theParentValue = this.DropDownOne;
// get the parent value
if theValue == null)
{
// if none
return null;
// return null
}
theChildren = theParentValue.MyChildren;
// get the child values for the parent
return theChildren;
// return it
}
Я пометил DisplayedValues
собственность как NonPersistent
потому что это необходимо только для пользовательского интерфейса DetailView.Я не думаю, что сохранение этого параметра ускорит создание коллекции в первый раз, и после того, как оно будет использовано для заполнения выпадающего списка, оно мне не понадобится, поэтому я не хочу тратить время на его хранение.
Проблема в том, что вызов занимает 45 секунд theParentValue = this.DropDownOne
.
Технические характеристики:
- Перспективный Бизнес
- 8 ГБ оперативной памяти
- Процессор E6550 с частотой 2,33 ГГц
- SQL Server Express 2005
Это слишком долго, чтобы пользователи могли ждать одного из многих выпадающих списков в детальном представлении.
Я потратил время на то, чтобы набросать бизнес-кейс, потому что у меня есть два вопроса:
Как я могу ускорить загрузку связанных значений?
Есть ли другой (простой) способ запрограммировать выпадающие списки и DetailView, который работает намного быстрее?
Да, вы можете сказать, что 630 - это слишком много элементов для отображения в выпадающем списке, но этот код занимает так много времени, что я подозреваю, что скорость пропорциональна 49 000, а не 630.100 элементов в выпадающем списке - это не слишком много для моего приложения.
Мне нужно довольно много таких выпадающих списков в моем приложении, поэтому нецелесообразно заставлять пользователя вводить более сложные критерии фильтрации для каждого из них.Пользователю необходимо выбрать одно значение и просмотреть связанные значения.
Я бы понял, если бы поиск большого количества записей был медленным, но поиск нескольких сотен не должен занять так много времени.
Решение
Во-первых, вы правы, скептически относясь к тому, что эта операция должна занимать так много времени, XPO при операциях чтения должен добавлять только 30-70% накладных расходов, и на этом крошечном объеме данных мы должны говорить о миллисекундах, а не о секундах.
Некоторые общие советы по совершенствованию доступны на форумах DevExpress и сосредоточены вокруг кэширования объектов, ленивой и глубокой загрузки и т.д., Но я думаю, что в вашем случае проблема в чем-то другом, к сожалению, очень трудно угадать, что происходит из вашего вопроса, только сказать, что это вряд ли будет проблемой с XPO, гораздо более вероятно, что это что-то другое, я был бы склонен взглянуть на создание вашего сеанса (это также создает ваш объектный кэш) и код подключения SQL (материал IDataStore), соединения часто медленные, если хосты не могут быть решены чисто, и если вы не объединяете / повторно -при использовании подключений эта проблема может усугубиться.
Другие советы
Я не уверен, почему ты делаешь это таким образом.Если вы создали такую ассоциацию, как эта:
public class A : XPObject
{
[Association("a<b", typeof(b))]
public XPCollection<b> bs { get { GetCollection("bs"); } }
}
public class B : XPObject
{
[Association("a<b") Persistent("Aid")]
public A a { get; set; }
}
затем, когда вы захотите заполнить выпадающий список (например, элемент управления LookUpEdit)
A myA = GetSomeParticularA();
lupAsBs.Properties.DataSource = myA.Bs;
lupAsBs.Properties.DisplayMember = "WhateverPropertyName";
Вам не нужно загружать дочерние элементы A, XPO загрузит их по мере необходимости, и для этого вообще не требуется управление сеансами.
Спасибо за ответ.Я создал отдельное решение и смог добиться хорошей производительности, как вы предлагаете.
Мое SQL-соединение в порядке и работает с другими функциями приложения.
Учитывая, что я использую XAF и не делаю ничего лишнего, разве мои сеансы не управляются XAF?
Сеанс, который я использую, считывается из DetailView.
Я не уверен в вашем случае, просто хочу поделиться своим опытом работы с XAF.
При первом нажатии на выпадающий элемент управления (список поиска) (в детальном представлении) в базу данных будут отправлены два запроса для заполнения списка.В моих тестах иногда весь объект загружается в исходную коллекцию, а не только свойства ID и Name, как мы думали, это зависит от ваших объектов, возможно, вы захотите использовать более легкие объекты для списков.Вы также можете включить серверный режим списка, тогда каждый раз загружается только 128 объектов.