Поскольку это все-таки форму по AXAPTA, а не филиал sql.ru, то я перевел это добро в синтаксис AXAPTA
PHP код:
static void Sum_Date_new(Args _args)
{
#AviFiles
SysOperationProgress sysOperationProgress;
Qty ostatok;
Int intLine,
progressTotal;
int startTime;
FromDate fromDate = 06\\05\\2005;
InventSum inventSum;
InventTrans inventTrans;
InventDim inventDim;
;
progressTotal = (select count(RecId) from inventSum).recId;
sysOperationProgress = new SysOperationProgress();
sysOperationProgress.setAnimation(#AviTransfer);
sysOperationProgress.setCaption('Расчет остатка на дату');
sysOperationProgress.setTotal(progressTotal);
sysOperationProgress.setText("Подготовка расчета...");
sysOperationProgress.update(true);
// Если надо, включаем режим грязного чтения
// inventSum.selectLocked(false);
startTime = timenow();
while select itemId, inventDimId, maxof(PhysicalInvent)
from inventSum
group by itemId, inventDimId
outer join sum(Qty)
from inventTrans
where inventTrans.ItemId == inventSum.ItemId
&& inventTrans.inventDimId == inventSum.InventDimId
&& ((inventTrans.DateInvent > fromDate)
|| (! inventTrans.DateInvent && inventTrans.DatePhysical > fromDate))
&& (inventTrans.StatusIssue == StatusIssue::Sold
|| inventTrans.StatusIssue == StatusIssue::Deducted
|| inventTrans.StatusIssue == StatusIssue::Picked
|| inventTrans.StatusReceipt == StatusReceipt::Purchased
|| inventTrans.StatusReceipt == StatusReceipt::Received
|| inventTrans.StatusReceipt == StatusReceipt::Registered)
exists join recId
from inventDim
where inventDim.inventDimId == inventSum.InventDimId
&& (inventDim.InventLocationId == 'Склад')
{
intLine++;
ostatok += inventSum.PhysicalInvent - inventTrans.Qty;
sysOperationProgress.setText(strFmt('Осталось %1 из %2',progressTotal-intLine,progressTotal));
sysOperationProgress.setCount(intLine);
}
sysOperationProgress.kill();
info(strfmt('Количество строк %1', intLine));
info(strfmt('На %1 остаток %2 шт', fromDate, ostatok));
info(strfmt('%1', 'Процесс успешно завершен'));
info(strfmt('Время длительности процесса: %1', time2str(timenow() - startTime,1,1)));
}
exists join по InventDim сделан, чтобы не возится с группировками еще и по полям из InventDim. Если делать напрямую в Query Analyzer, то можно заменить на INNER JOIN.
Так вот, большая и жирная ложка дегдя в этой бочке меда заключается в том, что такой запрос выполняется МЕДЛЕННЕЕ, чем цикл по InventSumDatePhysicalDim:: onHandQty()
На том же тестовом примере ЭТОТ запрос выполнялся примерно 1 час 20 минут. Через класс - около 50 минут. Результат одинаковый
Хотя, справедливости ради, следует отметить, что этот же самый запрос написанный напрямую в Query Analyzer выполнился примерно за минуту.