I want to know the fastest way to check if an array is empty in VB.NET. The array is already initialized so I can't use any of the checks that look at that. This is the current code below:
If Not (cubes(threadnumber)(i).objects.GetLength(0) = 0) Then
cubes(threadnumber)(i).objects = New Double() {}
ReDim cubes(threadnumber)(i).objects(-1)
End If
I've done some testing and I know that using .GetUpperBound is a little faster, but I'm not sure if this will work because I think .GetUpperBound returns a 0 if the array length is 1.
Any/all methods to speed this up (even fractionally) will be tremendously helpful. This program takes ages to compleate and the first line of the above code is a big portion of the time, it's called 136 million times.
Also if anyone knows how to speed up For...Next loops that'd be great too!
Length is about 2x faster than GetLength on my system (calling Length 136M times takes 0.650 seconds, while calling GetLength (0) takes 1.480 seconds).
I also do not understand why you ReDim your array, you've already created a new one.
I believe this will be the fastest code if cubes is a multi-dimensional array:
If cubes(threadnumber)(i).objects.Length > 0 Then
cubes(threadnumber)(i).objects = New Double() {}
End If
If cubes is not a multi-dimensional array (like List for instance), you should take the cubes(threadnumber) code out of the loop.
Update
Length is 6x faster than GetLength when running in Release mode without the debugger, in which case Length takes 0.181s and GetLength 1.175s on my system. This is likely because the JIT will inline the call to Length, but not the call to GetLength.
This is the test code I used.
if myarray is nothing then...
or
if myarray isnot nothing then...
GetLength is the fastest way I know of to see if an array has elements in it. I don't think you will speed up this piece of code.
However, the code that is calling this 136 million times could probably be optimised.
Looking at your code:
If Not (cubes(threadnumber)(i).objects.GetLength(0) = 0) Then
cubes(threadnumber)(i).objects = New Double() {}
ReDim cubes(threadnumber)(i).objects(-1)
End If
I'm guessing that the reason you are testing if it has elements is so you can redim the array to free up memory. A better way to free up memory might be to clear the cubes object instead and allow the arrays to fall out of scope.
After some intensive testing and analyzing I've found what appears to be the quickest method (so far at least). Making this small change has sped up my program 500-600%.
When there is an item added to the object arrays I also add the index of the second dimension of the cubes to a list IF the index of the second dimension is not already in the list. Any other suggest would be welcome though.
Related
Could someone provide some proofs, whether Ruby recalculates array size every time when you call array.size, array.length or array.count?
Thanks in advance.
Update
To make things clearer, by recalculate I mean, whether Ruby needs to loop through the whole array again and again to calculate the number of its elements every time when we call array.size.
Pragmatically Speaking, Array#length is Dynamic in Ruby
Your question can't really be answered canonically, because the lookup and storage implementations of arrays is often platform- and VM-specific. However, as a practical matter, from the Ruby interpreter's persepctive the answer is yes because each call sends a message to an Array object, asking it to return its current length.
Some languages store the current length of the array as an element of the array itself. Other approaches exist, too. In Ruby 2.7.1:
static VALUE
rb_ary_length(VALUE ary)
{
long len = RARRAY_LEN(ary);
return LONG2NUM(len);
}
the C implementation appears to retrieve the stored length of the array at the time of the call, but you'd have to dig deeper into the source code if you want to understand all the ins-and-outs of how the VM optimizes this (or not).
I have a class of objects known as blocks. Currently, I am creating an array of blocks using a for loop by simply tacking them unto an empty array
blockArray=[];
for ii=1:Size
blockArray=[blockArray block(....)];
end
In order to preallocate memory, how do I initialize an object array of blocks with dummy values?
For instance if instead of using block objects I used numbers, I could easily preallocate by using zeros(1,Size). Is there something similar that I could do?
The matlab documentation describes
To preallocate the object array, assign the last element of the array first. MATLAB® fills the first to penultimate array elements with default DocArrayExample objects.
So, to do this, instead of iterating over from 1:size, it is simpler to do...
blockArray = []
blockArray(size) = block(...)
The language does not really support this, there exists multiple solutions (or workarounds).
Replicating the first instance
When pushing the first element into the array, you can fill the whole array with this element to achieve a preallocation. This might look very bad, but it is actually the fastest possibility known to me.
for ii=1:S
%assumption e is a scalar, otherwise the code is totally screwed
e=block(....)
if ii==1
%to do preallocation, fill it with your first element
blockArray(1:S)=e
else
blockArray(ii)=e
end
end
Use cell arrays
Obvious simple solution, you can put any class into the fields
blockArray=cell(S,1);
for ii=1:S
%assumption e is a scalar, otherwise the code is totally screwed
e=block(....)
blockArray{ii}=e
end
This solution is very simple but slower than the first. You also lose some functionality which is not available for cell arras
Let your class implement array functionality
classdef A
properties
arg1
out
end
methods
function obj = A(varargin)
if nargin==0
%null object constructor
elseif strcmpi(varargin{1},'createarray')
sz=varargin(2:end);
%preallocate
obj(sz{:})=A;
else
%standard constructor
obj.arg1=varargin{1};
obj.out=[1 2 3;];
end
end
end
end
Constructor with no input argument creates an "empty" or "null" object, this is used to preallocate so it should be empty.
Constructor with first parameter makearray creates an array
Otherwise your constructor should be called.
Usage:
%create an empty object
A
%create an array of size 2,3,4
A('createarray',2,3,4)
%use the standard constructor
A(2)
Biggest downside is you have to modify your classes. Never tested this solution, but it should be close to the first in performance.
I have a application that will capture the screen and I want to write the captured information to an array, this takes AGES as the array ends up being +2million values. I am iterating and adding the values to the array, is there any way quicker (eg binary operations)? Should it be this slow? Why is it?
Assuming your GetPixel'ing the screen pixel by pixel, its the GetPixel call that's slow (it interrogates the display driver) not the (pre-dimensioned) array assignment.
You can instead use the getdibits() api which will copy the DC's colour info into a buffer in a single call.
Here is a C++ example, but the methodology & call sequence is the same as for VB.
Figured out why it was so slow, it was because I was using ReDim on every iteration of the loop - thanks for the help anyways
Martin
It seems to me that when creating an array of simple handle objects in Matlab time scales about linear. However, if I create exactly the same array and store it as a property of an object, time scales exponentially - so the program gets very slow when many objects are created.
My question is why this is happening and how it can be avoided?
Is the pre-allocation for object properties not properly implemented in my code or is there a fundamental problem with the way Matlab handles these things?
I wrote a simple test to illustrate the issue:
Code of simple Object:
classdef SomeSimpleObject < handle
% SomeSimpleObject defines an Object that has one property
properties
property=0;
end
methods
function SimpleObj=SomeSimpleObject()
if nargin~=0
SimpleObj.property=1;
end
end
end
end
Using the following Script to create a 1x10.000 array of these simple objects takes according to the profiler 0,4 sec on my machine:
for n=10000:-1:1 % counting backwards for Memory pre-allocation
ObjectList(n)=SomeSimpleObject();
end
However doing the same thing inside a class constructor and storing the array of 10.000 objects as a property takes 59 sec and it gets much worse quickly. Try it by creating an object from this class (e.g. a=HostingObject)
classdef HostingObject < handle
% This Objects Hosts a List of Objects that are created in the
% constructor
properties
ObjectList=SomeSimpleObject
end
methods
function obj=HostingObject()
for n=10000:-1:1 % counting backwards for Memory pre-allocation
obj.ObjectList(n)=SomeSimpleObject();
end
end
end
end
Searching for an Answer I came across a discussion on Matlab memory allocation and garbage collection. The Answer of Mikhail (also not directly related to my question) made me think that it might be a fundamental problem with the way Matlab implements objects, but I'm still not sure.
I don't know why your code is slow, but I found a way to fix it: use a cell array instead of a normal array. I don't find it completely intuitive myself, but here are my profiling results:
>> tic,a=HostingObject;toc
Elapsed time is 105.320128 seconds.
>> tic,a=JonasHostingObject;toc
Elapsed time is 2.394570 seconds.
The object is defined as follows:
classdef JonasHostingObject < handle
properties
ObjectList
end
methods
function obj=JonasHostingObject()
obj.ObjectList=cell(10000,1);
for n=1:10000
obj.ObjectList{n}=SomeSimpleObject();
end
end
end
end
I'm using MATLAB R2011a 64bit, in case it matters.
Inspired by the answers of #Jonas Heidelberg and #Tobias Heß I came up with the following solution that does not need cell arrays at all. The objects are stored in an auxiliary array and once this is completed they are copied to the property array:
Code for HostingObject with array "post-allocation":
classdef JacobHostingObject < handle
% This Objects Hosts a List of Objects that are created in the constructor
properties
ObjectList=SomeSimpleObject
end
methods
function obj=JacobHostingObject()
for n=10000:-1:1 % counting backwards for Memory pre-allocation
a(n)=SomeSimpleObject(); % auxiliary array for "post-allocation"
end
obj.ObjectList=a; % "post-allocation"
end
end
end
So how do the three solutions (Jonas, Tobias and mine) perform?
I ran some tests (with MATLAB R2011b 64bit) to compare them:
10.000 Objects
Elapsed Time: Tobias:0,30 sec; Jacob:0,31 sec; Jonas:2,02 sec; Original:56,79 sec
100.000 Objects
Elapsed Time: Tobias:2,42 sec; Jacob:2,95 sec; Jonas:203,03 sec
1.000.000 Objects
Elapsed Time: Tobias:23,84 sec; Jacob:29,18 sec
So it looks like Tobias version is the fastest solution
It is interesting to note, that Jonas solution is much better than the original but scales much worse to the other two solutions. This confirms the observation that I made in my earlier question "slow performance when storing handle objects in a cell array". It is a bit ironic that using the technique that was cause of my earlier problem turns out to be an improvement to this problem. Yet, Tobias solution even answers my old question as well (I will post a reference there).
However, it is still not clear what is actually going on inside MATLAB that causes the differences in performance. It might be helpful to get an understanding of this to avoid running into similar problems in the future!
I found an onther answer. I think using a cell array is not a good solution because you have not the same accsses to the objects as in an array. But you can use a cell as workaround for the problem:
classdef HostingObject < handle
% This Objects Hosts a List of Objects that are created in the
% constructor
properties
ObjectList=SomeSimpleObject
end
methods
function obj=HostingObject()
% Creating first a cell array
helpCell = cell(10000,1);
for n=1:10000
helpCell{n}=SomeSimpleObject();
end
% Convert the cell array to the object array
obj.ObjectList = horzcat(helpCell{:});
end
end
end
Is there an elegant way to express
val a = Array.fill(2,10) {1}
def do_to_elt(i:Int,j:Int) {
if (a.isDefinedAt(i) && a(i).isDefinedAt(j)) f(a(i)(j))
}
in scala?
I recommend that you not use arrays of arrays for 2D arrays, for three main reasons. First, it allows inconsistency: not all columns (or rows, take your pick) need to be the same size. Second, it is inefficient--you have to follow two pointers instead of one. Third, very few library functions exist that work transparently and usefully on arrays of arrays as 2D arrays.
Given these things, you should either use a library that supports 2D arrays, like scalala, or you should write your own. If you do the latter, among other things, this problem magically goes away.
So in terms of elegance: no, there isn't a way. But beyond that, the path you're starting on contains lots of inelegance; you would probably do best to step off of it quickly.
You just need to check the array at index i with isDefinedAt if it exists:
def do_to_elt(i:Int, j:Int): Unit =
if (a.isDefinedAt(i) && a(i).isDefinedAt(j)) f(a(i)(j))
EDIT: Missed that part about the elegant solution as I focused on the error in the code before your edit.
Concerning elegance: no, per se there is no way to express it in a more elegant way. Some might tell you to use the pimp-my-library-Pattern to make it look more elegant but in fact it does not in this case.
If your only use case is to execute a function with an element of a multidimensional array when the indices are valid then this code does that and you should use it. You could generalize the method by changing the signature of to take the function to apply to the element and maybe a value if the indices are invalid like this:
def do_to_elt[A](i: Int, j: Int)(f: Int => A, g: => A = ()) =
if (a.isDefinedAt(i) && a(i).isDefinedAt(j)) f(a(i)(j)) else g
but I would not change anything beyond this. This also does not look more elegant but widens your use case.
(Also: If you are working with arrays you mostly do that for performance reasons and in that case it might even be better to not use isDefinedAt but perform validity checks based on the length of the arrays.)