Thread overview | ||||||
---|---|---|---|---|---|---|
|
October 14, 2007 dynamic array initialized within a short function. | ||||
---|---|---|---|---|
| ||||
...I dare to repost my last message, now including a non-empty subject line. Hello! I realized that this code: int func() { int res; int[] g; g.length = 10; foreach(v; g) { res += v; } return res; } void main() { for(int i=0; i<10000000; i++) { func; } } runs about 7 times slower than this one: class Funcclass { int[] g; this() { g.length = 10; } int func() { int res; foreach(v; g) { res += v; } return res; } } void main() { auto fc = new Funcclass; for(int i=0; i<10000000; i++) { fc.func; } } The compilation was done with -O -release. The difference comes from all the memory-allocating and garbage collecting in the first case. My question is: Is it the default solution to put the function 'func' and the array 'g' as members into a common class? Or are there other / more elegant solutions for this? Thanks! |
October 14, 2007 Re: dynamic array initialized within a short function. | ||||
---|---|---|---|---|
| ||||
Posted in reply to coxalan |
coxalan wrote:
> ....I dare to repost my last message, now including a non-empty subject line.
>
>
> Hello!
>
> I realized that this code:
>
> int func() {
> int res;
> int[] g;
> g.length = 10;
> foreach(v; g) {
> res += v;
> }
> return res;
> }
>
> void main() {
> for(int i=0; i<10000000; i++) {
> func;
> }
> }
>
> runs about 7 times slower than this one:
>
> class Funcclass {
> int[] g;
>
> this() {
> g.length = 10;
> }
>
> int func() {
> int res;
> foreach(v; g) {
> res += v;
> }
> return res;
> }
> }
>
> void main() {
> auto fc = new Funcclass;
> for(int i=0; i<10000000; i++) {
> fc.func;
> }
> }
>
> The compilation was done with -O -release.
> The difference comes from all the memory-allocating and garbage collecting in the first case.
>
> My question is:
> Is it the default solution to put the function 'func' and the array 'g' as members into a common class?
> Or are there other / more elegant solutions for this?
>
> Thanks!
>
int func(int[] g) {
int res;
foreach(v; g) {
res += v;
}
return res;
}
void main() {
auto g = new int[10];
for(int i=0; i<10000000; i++) {
func(g);
}
}
In general, you should try and do as few allocations as possible. If you're using an array as "scratch space" -- that is, you don't care about what's in it before or after the function, only that it's there, it often help to allocate it earlier, and pass it into the function. Actually, you could add an overload of func like so:
int func() {
auto g = new int[10];
scope(exit) delete g;
return func(g);
}
Now both approaches work, and you can use whichever is most appropriate.
-- Daniel
|
October 14, 2007 Re: dynamic array initialized within a short function. | ||||
---|---|---|---|---|
| ||||
Posted in reply to Daniel Keep | Daniel Keep wrote:
> Actually, you could add an overload of func like so:
>
> int func() {
> auto g = new int[10];
> scope(exit) delete g;
> return func(g);
> }
>
> Now both approaches work, and you can use whichever is most appropriate.
If you're going to delete it anyway, and the length is a compile-time constant, you might as well pass a static array from the second function to the first instead.
Another option:
---
int func(int[] g = null) {
g.length = 10;
// original function code goes here
}
---
If a sufficiently-sized buffer is passed in, it's used. If not, a buffer is allocated. The main benefit over the 2-function approach is that only a single function is needed (so less clutter), but it does still heap-allocate when a new buffer is needed (and it doesn't delete such newly-allocated buffers).
|
October 17, 2007 Re: dynamic array initialized within a short function. | ||||
---|---|---|---|---|
| ||||
Posted in reply to Frits van Bommel | Thanks for your answers!
Frits van Bommel Wrote:
> Daniel Keep wrote:
> > Actually, you could add an overload of func like so:
> >
> > int func() {
> > auto g = new int[10];
> > scope(exit) delete g;
> > return func(g);
> > }
> >
> > Now both approaches work, and you can use whichever is most appropriate.
>
> If you're going to delete it anyway, and the length is a compile-time constant, you might as well pass a static array from the second function to the first instead.
>
> Another option:
> ---
> int func(int[] g = null) {
> g.length = 10;
> // original function code goes here
> }
> ---
> If a sufficiently-sized buffer is passed in, it's used. If not, a buffer is allocated. The main benefit over the 2-function approach is that only a single function is needed (so less clutter), but it does still heap-allocate when a new buffer is needed (and it doesn't delete such newly-allocated buffers).
Thanks for your answers!
|
Copyright © 1999-2021 by the D Language Foundation