forked from angular/angular
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(ivy): memoize array literals in render3 (angular#21973)
PR Close angular#21973
- Loading branch information
1 parent
f30f3e4
commit 829d87d
Showing
6 changed files
with
618 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,275 @@ | ||
/** | ||
* @license | ||
* Copyright Google Inc. All Rights Reserved. | ||
* | ||
* Use of this source code is governed by an MIT-style license that can be | ||
* found in the LICENSE file at https://angular.io/license | ||
*/ | ||
|
||
import {assertEqual} from './assert'; | ||
import {NO_CHANGE, bind, getTView} from './instructions'; | ||
|
||
|
||
/** | ||
* Updates an expression in an object literal if the expression has changed. | ||
* Used in objectLiteral instructions. | ||
* | ||
* @param obj Object to update | ||
* @param key Key to set in object | ||
* @param exp Expression to set at key | ||
* @returns Whether or not there has been a change | ||
*/ | ||
function updateBinding(obj: any, key: string | number, exp: any): boolean { | ||
if (bind(exp) !== NO_CHANGE) { | ||
obj[key] = exp; | ||
return true; | ||
} | ||
return false; | ||
} | ||
|
||
/** Updates two expressions in an object literal if they have changed. */ | ||
function updateBinding2(obj: any, key1: number, exp1: any, key2: number, exp2: any): boolean { | ||
let different = updateBinding(obj, key1, exp1); | ||
return updateBinding(obj, key2, exp2) || different; | ||
} | ||
|
||
/** Updates four expressions in an object literal if they have changed. */ | ||
function updateBinding4( | ||
obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, exp3: any, | ||
key4: number, exp4: any): boolean { | ||
let different = updateBinding2(obj, key1, exp1, key2, exp2); | ||
return updateBinding2(obj, key3, exp3, key4, exp4) || different; | ||
} | ||
|
||
/** | ||
* Gets a blueprint of an object or array if one has already been saved, or copies the | ||
* object and saves it for the next change detection run if it hasn't. | ||
*/ | ||
function getMutableBlueprint(index: number, obj: any): any { | ||
const tView = getTView(); | ||
const objectLiterals = tView.objectLiterals; | ||
if (objectLiterals && index < objectLiterals.length) { | ||
return objectLiterals[index]; | ||
} else { | ||
ngDevMode && objectLiterals && assertEqual(index, objectLiterals.length, 'index'); | ||
return (objectLiterals || (tView.objectLiterals = []))[index] = copyObject(obj); | ||
} | ||
} | ||
|
||
/** Copies an object or array */ | ||
function copyObject(obj: any): any { | ||
return Array.isArray(obj) ? obj.slice() : {...obj}; | ||
} | ||
|
||
/** | ||
* Updates the expression in the given object if it has changed and returns a copy of the object. | ||
* Or if the expression hasn't changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex Index of object blueprint in objectLiterals | ||
* @param obj Object to update | ||
* @param key Key to set in object | ||
* @param exp Expression to set at key | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral1(objIndex: number, obj: any, key: string | number, exp: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
if (bind(exp) === NO_CHANGE) { | ||
return NO_CHANGE; | ||
} else { | ||
obj[key] = exp; | ||
// Must copy to change identity when binding changes | ||
return copyObject(obj); | ||
} | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @returns A copy of the array or NO_CHANGE | ||
*/ | ||
export function objectLiteral2( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
return updateBinding2(obj, key1, exp1, key2, exp2) ? copyObject(obj) : NO_CHANGE; | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @param key3 | ||
* @param exp3 | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral3( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, | ||
exp3: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
let different = updateBinding2(obj, key1, exp1, key2, exp2); | ||
return updateBinding(obj, key3, exp3) || different ? copyObject(obj) : NO_CHANGE; | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @param key3 | ||
* @param exp3 | ||
* @param key4 | ||
* @param exp4 | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral4( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, | ||
exp3: any, key4: number, exp4: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
return updateBinding4(obj, key1, exp1, key2, exp2, key3, exp3, key4, exp4) ? copyObject(obj) : | ||
NO_CHANGE; | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @param key3 | ||
* @param exp3 | ||
* @param key4 | ||
* @param exp4 | ||
* @param key5 | ||
* @param exp5 | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral5( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, | ||
exp3: any, key4: number, exp4: any, key5: number, exp5: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
let different = updateBinding4(obj, key1, exp1, key2, exp2, key3, exp3, key4, exp4); | ||
return updateBinding(obj, key5, exp5) || different ? copyObject(obj) : NO_CHANGE; | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @param key3 | ||
* @param exp3 | ||
* @param key4 | ||
* @param exp4 | ||
* @param key5 | ||
* @param exp5 | ||
* @param key6 | ||
* @param exp6 | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral6( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, | ||
exp3: any, key4: number, exp4: any, key5: number, exp5: any, key6: number, exp6: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
let different = updateBinding4(obj, key1, exp1, key2, exp2, key3, exp3, key4, exp4); | ||
return updateBinding2(obj, key5, exp5, key6, exp6) || different ? copyObject(obj) : NO_CHANGE; | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @param key3 | ||
* @param exp3 | ||
* @param key4 | ||
* @param exp4 | ||
* @param key5 | ||
* @param exp5 | ||
* @param key6 | ||
* @param exp6 | ||
* @param key7 | ||
* @param exp7 | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral7( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, | ||
exp3: any, key4: number, exp4: any, key5: number, exp5: any, key6: number, exp6: any, | ||
key7: number, exp7: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
let different = updateBinding4(obj, key1, exp1, key2, exp2, key3, exp3, key4, exp4); | ||
different = updateBinding2(obj, key5, exp5, key6, exp6) || different; | ||
return updateBinding(obj, key7, exp7) || different ? copyObject(obj) : NO_CHANGE; | ||
} | ||
|
||
/** | ||
* Updates the expressions in the given object if they have changed and returns a copy of the | ||
* object. | ||
* Or if no expressions have changed, returns NO_CHANGE. | ||
* | ||
* @param objIndex | ||
* @param obj | ||
* @param key1 | ||
* @param exp1 | ||
* @param key2 | ||
* @param exp2 | ||
* @param key3 | ||
* @param exp3 | ||
* @param key4 | ||
* @param exp4 | ||
* @param key5 | ||
* @param exp5 | ||
* @param key6 | ||
* @param exp6 | ||
* @param key7 | ||
* @param exp7 | ||
* @param key8 | ||
* @param exp8 | ||
* @returns A copy of the object or NO_CHANGE | ||
*/ | ||
export function objectLiteral8( | ||
objIndex: number, obj: any, key1: number, exp1: any, key2: number, exp2: any, key3: number, | ||
exp3: any, key4: number, exp4: any, key5: number, exp5: any, key6: number, exp6: any, | ||
key7: number, exp7: any, key8: number, exp8: any): any { | ||
obj = getMutableBlueprint(objIndex, obj); | ||
let different = updateBinding4(obj, key1, exp1, key2, exp2, key3, exp3, key4, exp4); | ||
return updateBinding4(obj, key5, exp5, key6, exp6, key7, exp7, key8, exp8) || different ? | ||
copyObject(obj) : | ||
NO_CHANGE; | ||
} |
Oops, something went wrong.