From 1320175646e7c6341313a34974149a7203d73d1c Mon Sep 17 00:00:00 2001 From: Stephen Adams Date: Wed, 7 Jan 2015 11:47:25 -0800 Subject: [PATCH] perf(change detection): minimized amount of code in protective try-catch --- .../change_detection/src/change_detector.js | 60 +++++++------------ modules/change_detection/src/record.js | 30 +++++++++- 2 files changed, 48 insertions(+), 42 deletions(-) diff --git a/modules/change_detection/src/change_detector.js b/modules/change_detection/src/change_detector.js index 6481c58971..2522245490 100644 --- a/modules/change_detection/src/change_detector.js +++ b/modules/change_detection/src/change_detector.js @@ -19,22 +19,6 @@ class ExpressionChangedAfterItHasBeenChecked extends Error { } } -export class ChangeDetectionError extends Error { - message:string; - originalException:any; - location:string; - - constructor(record:Record, originalException:any) { - this.originalException = originalException; - this.location = record.protoRecord.expressionAsString; - this.message = `${this.originalException} in [${this.location}]`; - } - - toString():string { - return this.message; - } -} - export class ChangeDetector { _rootRecordRange:RecordRange; _enforceNoNewChanges:boolean; @@ -58,32 +42,28 @@ export class ChangeDetector { var record = this._rootRecordRange.findFirstEnabledRecord(); var currentRange, currentGroup; - try { - while (isPresent(record)) { - if (record.check()) { - count++; - if (record.terminatesExpression()) { - if (throwOnChange) throw new ExpressionChangedAfterItHasBeenChecked(record); - currentRange = record.recordRange; - currentGroup = record.groupMemento(); - updatedRecords = this._addRecord(updatedRecords, record); - } + while (isPresent(record)) { + if (record.check()) { + count++; + if (record.terminatesExpression()) { + if (throwOnChange) throw new ExpressionChangedAfterItHasBeenChecked(record); + currentRange = record.recordRange; + currentGroup = record.groupMemento(); + updatedRecords = this._addRecord(updatedRecords, record); } - - if (isPresent(updatedRecords)) { - var nextEnabled = record.nextEnabled; - if (isBlank(nextEnabled) || // we have reached the last enabled record - currentRange != nextEnabled.recordRange || // the next record is in a different range - currentGroup != nextEnabled.groupMemento()) { // the next record is in a different group - currentRange.dispatcher.onRecordChange(currentGroup, updatedRecords); - updatedRecords = null; - } - } - - record = record.findNextEnabled(); } - } catch(e) { - throw new ChangeDetectionError(record, e); + + if (isPresent(updatedRecords)) { + var nextEnabled = record.nextEnabled; + if (isBlank(nextEnabled) || // we have reached the last enabled record + currentRange != nextEnabled.recordRange || // the next record is in a different range + currentGroup != nextEnabled.groupMemento()) { // the next record is in a different group + currentRange.dispatcher.onRecordChange(currentGroup, updatedRecords); + updatedRecords = null; + } + } + + record = record.findNextEnabled(); } return count; diff --git a/modules/change_detection/src/record.js b/modules/change_detection/src/record.js index 0840dfbc0c..c0352a7cb3 100644 --- a/modules/change_detection/src/record.js +++ b/modules/change_detection/src/record.js @@ -274,12 +274,22 @@ export class Record { } _calculateNewValue() { + try { + return this.__calculateNewValue(); + } catch (e) { + throw new ChangeDetectionError(this, e); + } + } + + __calculateNewValue() { switch (this.getType()) { case RECORD_TYPE_PROPERTY: - return this.funcOrValue(this.context); + var propertyGetter:Function = this.funcOrValue; + return propertyGetter(this.context); case RECORD_TYPE_INVOKE_METHOD: - return this.funcOrValue(this.context, this.args); + var methodInvoker:Function = this.funcOrValue; + return methodInvoker(this.context, this.args); case RECORD_TYPE_INVOKE_CLOSURE: return FunctionWrapper.apply(this.context, this.args); @@ -477,3 +487,19 @@ function isSame(a, b) { if ((a !== a) && (b !== b)) return true; return false; } + +export class ChangeDetectionError extends Error { + message:string; + originalException:any; + location:string; + + constructor(record:Record, originalException:any) { + this.originalException = originalException; + this.location = record.protoRecord.expressionAsString; + this.message = `${this.originalException} in [${this.location}]`; + } + + toString():string { + return this.message; + } +}