0

Given the following expression in C#, and that chunkWidth and chunkHeight are fixed pre-calculated numbers, is it possible to optimise the expression by perhaps pre-computing part of the modulo division beforehand?

// Once assigned these guys never change
private int _chunkWidth;
private int _chunkHeight;

// This function needs to be super optimal!
SomeObject LookupObject(int row, int column) {
    int index = (row % _chunkHeight) * _chunkWidth + (column % _chunkWidth);
    return _objects[ index ];
}
Lea Hayes
  • 56,578
  • 16
  • 55
  • 104
  • If they never change why aren't they defined as constants?? This MAY provide some optimization. Now in general terms I do not see any other thing you can do to optimize this... – Angelos Chalaris Oct 14 '12 at 14:51
  • @Spiritios they cannot be constants because they get calculated when the data structure is generated. – Lea Hayes Oct 14 '12 at 14:53
  • Are you sure this is not a case of the XY problem(http://meta.stackexchange.com/questions/66377/what-is-the-xy-problem)? Are you totally sure that the problem lies in optimizing this rather than in the larger picture? :) – Angelos Chalaris Oct 14 '12 at 14:57
  • @Spiritios possibly, I have a chunked data structure (which has gaps where there is no data). To access an individual item my code first looks up the chunk (`SomeObject`) and then looks up the item in that chunk. So there are in total 3 `%`'s to access a single item. And item access is extremely frequent and is causing some noticeable slowdown as it's often called thousands of times per frame. – Lea Hayes Oct 14 '12 at 14:59
  • I would look to classes and method calls as a possible bottleneck before I looked at modulos and multiplications. – jrajav Oct 14 '12 at 15:05
  • @Kiyura Do you mean perhaps create a hybrid function which inlines the second accessor resulting in one method call instead of two? – Lea Hayes Oct 14 '12 at 15:07
  • Speaking of which, does the .NET compiler (or JIT) perform inlines on functions in C#? – Lea Hayes Oct 14 '12 at 15:10
  • No, I meant that I would see if I could store the data in a struct or an array and access it directly in a loop rather than branching. Classes and method calls in C# have noticeable overhead if we're talking about realtime graphics. (In fact, I probably wouldn't have chosen C# for this.) – jrajav Oct 14 '12 at 15:11
  • @Kiyura Well I have two choices really. There are four data fields per item. I can either store those in a class or store them as 4 parallel arrays. Due to a technical limitation with the platform that I am using I cannot use structs (which I would prefer if it were possible). Would 4 parallel array lookups be better than looking up and using class instances? – Lea Hayes Oct 14 '12 at 15:18
  • Yes. And if you want to make it extra simple for the runtime to optimize, try to access the arrays linearly (if you just looked up 43, look up 44 next). – jrajav Oct 14 '12 at 15:30
  • Thanks @Kiyura I will spend some time experimenting with that – Lea Hayes Oct 14 '12 at 15:35

2 Answers2

3

To allow the variables to only be assigned once, you can add the readonly attribute to them. This may allow some optimizations. I wouldn't be terribly worried about the performance of basic arithmetic operations, though, not unless this has proven to be an extremely tight bottleneck.

jrajav
  • 5,208
  • 1
  • 21
  • 32
  • I might be able to reorganise the class a little so that they can be assigned using the constructor and thus be marked as `readonly`. At the moment the class is created earlier and initialised when it is first accessed. – Lea Hayes Oct 14 '12 at 14:54
  • This is new for me, can you share some reference regarding performance boost with the help of readonly fields? Since i thought this is only possible with const field. – Furqan Safdar Oct 14 '12 at 14:59
  • @FurqanSafdar, that's a good question. I had assumed it would aid performance optimizations, but apparently it does not: http://www.dotnetperls.com/readonly http://stackoverflow.com/questions/277010/what-are-the-benefits-to-marking-a-field-as-readonly-in-c So really, the only reason you should use readonly is to improve the clarity of your code (which is still an excellent reason). – jrajav Oct 14 '12 at 15:04
1

Even if chunkWidth and chunkHeight are fixed and pre-calculated fields, but still you cannot further optimize the modulo operation since row and column are variables which requires modulo operation each time the statement is executed.

Furqan Safdar
  • 14,930
  • 12
  • 52
  • 85
  • I thought that might be the case, I saw that `%` was the same as `A - B * (A / B)` so I wasn't sure if perhaps part could be recalculated. My initial thoughts were to pre-calculate `1 / B` and then just multiply when I soon realised that would be impossible given that I am working with integer division. – Lea Hayes Oct 14 '12 at 14:57