Truecolors Ответов: 1

Как улучшить хранимую процедуру, вызывающую функцию?


У меня есть функция, которая вызывается в 3 разных хранимых процедурах, но я работаю над одной хранимой процедурой и пытаюсь улучшить ее производительность с 3 минут до нескольких секунд.


Я могу ошибаться, но я считаю, что проблемы, которые вызывают эти проблемы, заключаются в том, что
1) функция использует табличные переменные и
2) он возвращает больше информации, чем мне нужно для хранимой процедуры, над которой я работаю. Я делаю
select distinct
в моем sp выбрать только те поля, которые мне нужны, но так как функция используется для других SP, я не могу изменить эту функцию.


Я думал исправить это, создав новую хранимую процедуру с временными таблицами вместо табличной переменной и вызвав новый SP в исходном, в котором я работал. У меня возникли некоторые проблемы с его работой, поэтому я хотел бы знать, есть ли другие способы улучшить производительность хранимой процедуры, которая вызывает возобновляемую функцию?


Я просто хочу изучить различные способы или варианты повышения эффективности этой процедуры.

Любая помощь или информация будут очень полезны и оценены. Спасибо.

Что я уже пробовал:

Оригинальный Хранимой Процедуры
Select Distinct
  osParticipantPK,
  osEntityPK,
  VendorTaxID,
  VendorEntityID,
  VendorFullName,
  VendorFileNameAs,
  IsActive,

  LastPmtDate,
  TotalAmountPaid,
  TotalCommitmentToPayBalance,
  MailingAddress
 
From
  dbo.apfGetVendorComitments(@osCompanyModulePK,
                             @ReferenceDate,
                             @ParticipantStatus,
                             @ShowCmmToPayBalanceOnly,
                             @osParticipantPKs)
Order By VendorFullName



Переменная возвращаемой таблицы функции возвращает все это
Returns @apVendorsToReturn Table 
(
  tnHeaderPk Int Null,
  tnSummaryTranPK Int Null,
  tnSummaryTranlktnTranOriginal Int Null,
  tnTranPK Int Null,
  osParticipantPK Int Null,
  osEntityPK Int Null,
  VendorTaxID Varchar (15) Null,
  VendorEntityID Varchar (20) Null,
  VendorFullName Varchar (128) Null,
  VendorFileNameAs Varchar (128) Null,
  IsActive Varchar (3) Null,
  InvoiceNumber Varchar (20) Null,
  PurchaseOrderNumber Varchar (20) Null,
  LastPmtDate DateTime Null,
  TotalAmountPaid Numeric(19,4) Null,
  CommitmentToPayBalance Numeric (19,4) Null,
  TotalCommitmentToPayBalance Numeric (19,4) Null, -- (Total By Vendor)
  DueDate DateTime Null,
  tnTranDescription Varchar(50) Null,
  IsAdjustment Varchar(3) Null,

  tnHeaderfkosCompanyModule Int Null,
  tnHeaderfkMLStnHeaderType Int Null,

  tnHeaderOpenStatus Varchar(50) Null,
  tnHeaderPostStatus Varchar(50) Null,
  tnHeaderPaymentStatus Varchar(50) Null,
  tnTranStatus Varchar(50) Null,
  CommitmentStatus Varchar(50) Null,

  apTranIsMinorityOwned Varchar (3) Null,
  apTranIsWomanOwned Varchar (3) Null,

  MailingAddress Varchar(255) Null,

  -- Commitments Header (CH) :
  -- 5 more fields
)


Может ли проблема быть связана с несколькими соединениями в этом операторе Select?

tnHeader.pk,
  tnSummaryTran.pk As tnSummaryTranPK,
  tnSummaryTran.lktnTranOriginal As tnSummaryTranlktnTranOriginal,
  tnTran.pk As tnTranPK,

  osParticipant.PK As osParticipantPK,
  osEntity.PK As osEntityPK,

  VendorTaxID = 
    Case 
      When @UseDisguisedTaxID = 'Yes' Then osEntity.DisguisedTaxID
      Else osEntity.TaxID
    End,

  osEntity.EntityID As VendorEntityID,
  osEntity.FullName As VendorFullName,
  osEntity.FileNameAs As VendorFileNameAs,
  IsNull(osParticipant.IsActive, 'No') As IsActive,
  ......... many other fields.....
  MailingAddress = Null,           -- Populate later using function

  
From 
  tnSummaryTran  WITH (NOLOCK) 
  Join tnTran WITH (NOLOCK) on tnTran.pk = tnSummaryTran.lktnTranOriginal
  Join tnHeader WITH (NOLOCK) on tnHeader.pk = tnSummaryTran.fktnHeader
  Join apHeader WITH (NOLOCK) on apHeader.fktnHeader = tnHeader.pk
  Join apTran WITH (NOLOCK) on apTran.fktnTran = tnTran.pk
  Join osControlNumberStatus osControlNumbertnHeaderOpenStatus WITH (NOLOCK) on osControlNumbertnHeaderOpenStatus.pk = tnHeader.fkosControlNumberOpenStatus
  Join osControlNumberStatus osControlNumberOpenStatus WITH (NOLOCK) on osControlNumberOpenStatus.pk = tnTran.fkosControlNumberStatus
  Join tnSummaryTran tnSummaryTranOriginal WITH (NOLOCK) on tnSummaryTranOriginal.pk = dbo.tnfInitialSummaryTranPK(tnSummaryTran.pk)
  Join tnHeader tnHeaderReference WITH (NOLOCK) on tnHeaderReference.pk = tnSummarytranOriginal.fktnHeader
  Join osParticipant WITH (NOLOCK) on osParticipant.pk = tnHeader.fkosParticipant  
  Join apVendor WITH (NOLOCK) on apVendor.fkosparticipant = osparticipant.pk
  Join osEntity WITH (NOLOCK) on osEntity.pk = osParticipant.fkosEntity
  Left Join osControlNumberStatus osControlNumbertnHeaderPostStatus WITH (NOLOCK) on osControlNumbertnHeaderPostStatus.pk = tnHeader.fkosControlNumberPostStatus
  Left Join osControlNumberStatus osControlNumbertnHeaderPaymentStatus WITH (NOLOCK) on osControlNumbertnHeaderPaymentStatus.pk = tnHeader.fkosControlNumberPaymentStatus

  -- Get Commitment Header (Type 9):
  Left Join apHeader apHeaderCommHeader WITH (NOLOCK) on apHeaderCommHeader.fktnHeader = tnHeader.lktnHeaderReference
  Left Join tnHeader tnHeaderCommHeader WITH (NOLOCK) on tnHeaderCommHeader.pk = tnHeader.lktnHeaderReference


Where 
  tnSummaryTran.fktnHeader Is Not Null

RossMW

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

Попробуйте запустить эту функцию самостоятельно. Вероятно, именно здесь и кроется проблема скорости.

[no name]

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

RossMW

Возможно. Проблемы Peformance могут быть рядом вещей, которые мы не смогли бы определить, не видя структуру и детали таблиц.

Некоторые из возможных областей
- размер таблицы
- ключевые поля правильно проиндексированы
- тип поля, используемого для соединений
- Аппаратное обеспечение и т. д

Вам нужно будет разобрать его и провести тестирование, профилирование, чтобы определить, где находится настоящая проблема.

Maciej Los

Звучит как ответ на мой вопрос.

RossMW

Никогда не бывает слишком уверен в этих смутных вопросах. По вашему совету я выложу в качестве ответа

1 Ответов

Рейтинг:
1

RossMW

Truecolors писал:

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


Возможно. Проблемы Peformance могут быть рядом вещей, которые мы не смогли бы определить, не видя структуру и детали таблиц.

Некоторые из возможных областей
- размер таблицы
- ключевые поля правильно проиндексированы
- тип поля, используемого для соединений
- Аппаратное обеспечение и т. д

Вам нужно будет разобрать его и провести тестирование, профилирование, чтобы определить, где находится настоящая проблема.


Maciej Los

5ед!