c# - Caching variables in a `for` loop -


i've been reading tips javascript performance boosting , 1 tip said cache variables (that don't change) in loops comparer statement , wondering if applied .net.

assuming had simple loop, 1 of following faster or same?

no cache:

for (int = 0; < somearray.length; i++) {  } 

with cache:

for (int = 0, count = somearray.length; < count; i++) {  } 

according article "caching" value of length cuts out 1 operation in loop because faster access local variables compared accessing members of object. faster declaring local variable compared accessing member? compiler pick on , automatically cache value? there negatives in declaring local variable on accessing member?

whilst speed key factor here, not one. next question 1 more efficient. uses less memory allocations? performs less stack manipulation? etc...

from comments, seems accessing array lengths pretty fast. lets use ilist<> instead. caching value of count faster retrieving each iteration?

in compiled language, you're doing premature optimization. suppose interpreted language might save bit, there feels payoff minimal (in experience) unusual way code loop.

to answer question directly c#, no, compiler not optimize caching. create new array new length during loop. such, load array length every time evaluates stop condition. or worse, may not using "traditional" style stop conditions , may need evaluate function know stop.

that said, here's simple program:

static void main( string[] args ) {     int[] integers = new int[] { 1, 2, 3, 4, 5 };      for( int = 0; < integers.length; i++ ) {         console.writeline( );     } } 

and here's il (with nops removed):

il_000d:  call       void [mscorlib]system.runtime.compilerservices.runtimehelpers::initializearray(class [mscorlib]system.array,                                                                                                      valuetype [mscorlib]system.runtimefieldhandle) il_0012:  stloc.0 il_0013:  ldc.i4.0 il_0014:  stloc.1 il_0015:  br.s       il_0024 il_0018:  ldloc.1 il_0019:  call       void [mscorlib]system.console::writeline(int32) il_0020:  ldloc.1 il_0021:  ldc.i4.1 il_0022:  add il_0023:  stloc.1 il_0024:  ldloc.1 il_0025:  ldloc.0 il_0026:  ldlen il_0027:  conv.i4 il_0028:  clt il_002a:  stloc.2 il_002b:  ldloc.2 il_002c:  brtrue.s   il_0017 

the key answer question here, is pushing array location 0 in stack, during il_0026 performing call length of array, il_0028 performing less comparison, , going il_0017 if evaluation true.

by caching length of array, you're saving ldlen , stloc call. ldlen instruction should fast getting length of array not of time waster.

edit:

the primary difference list instruction:

il_002b:  callvirt   instance int32 class [mscorlib]system.collections.generic.list`1<int32>::get_count() 

callvirt take more time, function realistically return private variable.

you'd way better off worrying things take milliseconds - chunking database calls, or optimizing sql queries they're faster, etc, trying shave off single il operations.


Comments

Popular posts from this blog

SPSS keyboard combination alters encoding -

Add new record to the table by click on the button in Microsoft Access -

javascript - jQuery .height() return 0 when visible but non-0 when hidden -