大量のデータを扱うことは、1C開発者が直面する最も一般的な問題の1つです。レポートの遅延、処理の停止、ユーザーの不満はすべて、データの取り扱い方が間違っていることが原因です。正しい方法を見てみましょう。
パフォーマンスの問題が発生するのはなぜですか?
データベースに数千のドキュメントがある場合、すべてが迅速に動作します。しかし、データが数十万または数百万のレコードに増加すると、以前は瞬時に実行されていたコードが数分で動作し始めます。理由は簡単です。データベースへのアクセスには時間がかかり、最適化されていないクエリは必要以上に多くのデータを処理する可能性があります。
ビッグデータの基本原則
1. ループの代わりにクエリを使用する
初心者の開発者の最も一般的な間違いは、ループでのデータ処理です。たとえば、倉庫内の商品の残高を取得する必要がある場合は、ループ内のすべての商品を並べ替えて、それぞれに個別のリクエストを行う必要はありません。
❌悪い:
Для Каждого Товар Из СписокТоваров Цикл
Запрос = Новый Запрос;
Запрос.Текст = "SELECT Remainder WHERE Nomenclature = &Nomenclature";
Запрос.УстановитьПараметр("Nomenclature", Товар);
// 何百回も実行されます!
КонецЦикла;✅ 良い:
Запрос = Новый Запрос;
Запрос.Текст =
"SELECT
| Nomenclature,
| Balance
|FROM RegisterAccumulation.BalanceGoods.Balance
|WHERE Nomenclature IN (&List of Goods)";
Запрос.УстановитьПараметр("List of goods", СписокТоваров);
// 一度だけ実行されます!重要: 何百もの代わりに1つのリクエストは、1秒と1分の作業の違いです。
2.データの選択を制限する
必要ない場合は、すべてのフィールドを読み込まないでください。一部のみが必要な場合は、すべてのエントリを選択しないでください。
// 必要なフィールドのみを選択します
Запрос.Текст =
"SELECT
| Document.Number,
| Document.Date,
| Document.Amount
| FROM Document.SaleOfGoodsServices AS Document
|WHERE Document.Date BETWEEN &StartDate AND &EndDate
| AND Document.Posted = TRUE";すべてのレコードを取得した後、コード内ではなく、データベースレベルでデータをフィルタリングするには、WHERE条件を使用します。
3. インデックスを適用する
インデックスは、データベースの検索を高速化するものです。1Cでは、インデックス可能としてマークされた属性に対してインデックスが自動的に作成されます。特定の属性でデータを頻繁にフィルタリングする場合は、その属性にインデックスが作成されていることを確認してください。
4. 一時テーブルを使用する
相互に関連する複数のクエリを実行する必要がある場合、一時テーブルは中間結果を保存し、メインテーブルに再度アクセスしないようにするのに役立ちます。
Запрос = Новый Запрос;
Запрос.Текст =
"SELECT
| Counterparty,
| AMOUNT (Amount) AS TotalAmount
| PLACE InAmountsByCounterparties | FROM Document.SaleOfGoodsServices
| GROUP BY Counterparty |; | | SELECT
| InAmountsByCounterparties.Counterparty,
| InAmountsByCounterparties.TotalAmount
| FROM VtAmountsByCounterparties | WHERE VtAmountsByCounterparties.TotalAmount> 100000";
5. パッケージで作業する
100万件のレコードを処理する必要がある場合は、すべてを一度に読み込まないでください。1000〜10000レコードのバッチでデータを処理します。
СчётчикПорции = 0;
РазмерПорции = 5000;
Пока Истина Цикл
Запрос.Текст =
"SELECT FIRST " + РазмерПорции + "
| Link
|FROM Reference Book.Nomenclature
| WHERE Link> & LastLink | SORT BY Link";
Результат = Запрос.Выполнить();
Если Результат.Пустой() Тогда
Прервать;
КонецЕсли;
// 一部分を処理しています
Выборка = Результат.Выбрать();
Пока Выборка.Следующий() Цикл
// アイテムの処理
ПоследняяСсылка = Выборка.Ссылка;
КонецЦикла;
КонецЦикла;6.累積レジスタを正しく使用する
累積レジスタは、定量データを扱うための強力なツールです。これにより、動きの履歴全体を再計算することなく、残高と売上高をすばやく取得できます。
// 日付の残高を取得する
Запрос.Текст =
"SELECT
| Remainders.Nomenclature,
| Remainders.QuantityRemainder
| FROM AccumulationRegister. GoodsInWarehouses. Remains (& Date) AS Remains";7. テーブルの結合を最適化する
クエリで接続(JOIN)を使用する場合、接続の順序と種類が重要です。最初に、レコード数が最も少ないテーブルを結合します。
実用的なアドバイス
クエリプランを分析します。 1Cクエリコンソールでは、クエリがどのように実行され、ボトルネックが発生する場所を確認できます。
パフォーマンス測定を使用します。 1Cの組み込みツールを使用すると、遅い操作を見つけることができます。推測ではなく、測定してください!
ネストされたクエリは避けてください。 ほとんどの場合、それらをより良いパフォーマンスを持つ結合または一時テーブルに置き換えることができます。
変更不可能なデータをキャッシュします。 データがめったに変わらない場合は、モジュールの変数に保存するか、キャッシュ可能な情報レジスタを使用してください。
よくある間違い
必要なフィールドを明示的に列挙する代わりに、「*を選択」を介してすべてのフィールドを取得する
事前計算の代わりにWHERE条件で複雑な計算を使用する
選択を制限できるフィルタリング条件がない
1つのバッチリクエストではなく、データベースへの複数のリクエスト
結論
1Cでビッグデータを扱うには、データベースとクエリの仕組みを理解する必要があります。基本的なルールは簡単です。データベースへのアクセス数を最小限に抑え、ループの代わりにクエリを使用し、必要なデータのみを選択し、適切なタスクに適切なツールを使用します。
最適化は、コードを早期に複雑にすることではなく、最初から適切に設計することであることを忘れないでください。効率的なクエリを書く習慣を身につけることで、将来的にデバッグに費やす時間や最適化に費やす時間を節約できます。
🚀もっと詳しく知りたいですか?
このトピックやその他の多くのトピックは、 コディケ — 初心者向けの開発者プラットフォームです!ゼロから自信を持って開発を習得するのに役立つ構造化されたコースを作成しました。
また、当社には フレンドリーなコミュニティのクールなテレグラムチャンネル経験豊富な開発者が初心者を支援し、経験を共有し、現在のプログラミングの問題について話し合う場所です。
