473,408 Members | 2,030 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,408 software developers and data experts.

Optimization needed... Is Assembly code available?

Hi,
I need to optimize a close loop. Usually I would use assembly, but I don't
event know if it's available to VB.NET. I'll explain the case and maybe some
of you will be able to advise me.

I have a byte() (byte array) containing about 100,000 elements (a bit less,
but always is around 80,000-95,000). I need to take the data from it as
int16 and compare the int16 to a reference value

for now, I'm using a MemoryStream created from the byte(), a BinaryReader
that reads from the MemoryStream (ReadInt16) and then compare the int16 to a
reference value and return false if the int16 is greater than the reference
value. if all the values are lower than the reference value, then the
function returns true. If it returns after the first loop or so, it's ok,
but if it runs through all the elements it's way too long. In assembly it
would take way less time than that, because I could move the reference value
in one of the CPU's register and leave it there as long as my loop runs and
iterate directly in the byte() to get 2 bytes at a time.

In VB.NET it's a function that stands in about 10 lines of code (maybe even
lower), but it takes up to 50% of the CPU (when looked in the task manager)
which is way too much because it runs very often. When it does not run (many
other things are running in the app), the app takes about 1%-2% of the CPU,
when this close loop starts being called, the app get's to 30%-50% of the
CPU... it's a bit excessive due to the fact that the function is called
about 8-10 times a second.

thanks for your help

ThunderMusic
Feb 20 '06 #1
10 1460

FYI, there's a group dedicated to performance issues;
microsoft.public.dotnet.framework.performance

I need to optimize a close loop. Usually I would use assembly, but I don't
event know if it's available to VB.NET.


It isn't, but you can certainly write assembly code, compile to a DLL
and call that from VB.NET if you want.

You could also try using pointers in C# (unsafe code) or C++ to walk
the array.

In any case I wouldn't worry too much about the CPU utilization, more
about the time spent in the loop. Use a profiler!
Mattias

--
Mattias Sjögren [C# MVP] mattias @ mvps.org
http://www.msjogren.net/dotnet/ | http://www.dotnetinterop.com
Please reply only to the newsgroup.
Feb 20 '06 #2

"Mattias Sjögren" <ma********************@mvps.org> wrote in message
news:u%****************@tk2msftngp13.phx.gbl...

FYI, there's a group dedicated to performance issues;
microsoft.public.dotnet.framework.performance


thanks a lot, I didn't know because it's the first time I have a real
performance issue, so I'll use a profiler (as advised) and try posting
there. Thanks a lot.

ThunderMusic
Feb 20 '06 #3
ThunderMusic wrote:
I need to optimize a close loop. Usually I would use assembly, but I
don't event know if it's available to VB.NET. I'll explain the case
and maybe some of you will be able to advise me.


To answer your original question, it is not normally possible to write
inline assembly in a .NET language, because .NET assemblies are intended to
be portable between platforms. However, there are techniques by which you
can include inline CLR bytecode, which is handy when either you need to
optimize a hotspot or you need access to a CLR feature that your language
does not give access to. There is a tool available here, written by Mike
Stall, that enables this:

http://blogs.msdn.com/jmstall/archiv...21/377806.aspx

--
Derrick Coetzee, MCAD, MSFT (Speech Server)
This posting is provided "AS IS" with no warranties, and confers no
rights.
Feb 20 '06 #4
ThunderMusic <NOdanlatSPAM@hotmaildotcom> wrote:
I need to optimize a close loop. Usually I would use assembly, but I don't
event know if it's available to VB.NET. I'll explain the case and maybe some
of you will be able to advise me.

I have a byte() (byte array) containing about 100,000 elements (a bit less,
but always is around 80,000-95,000). I need to take the data from it as
int16 and compare the int16 to a reference value

for now, I'm using a MemoryStream created from the byte(), a BinaryReader
that reads from the MemoryStream (ReadInt16) and then compare the int16 to a
reference value and return false if the int16 is greater than the reference
value. if all the values are lower than the reference value, then the
function returns true. If it returns after the first loop or so, it's ok,
but if it runs through all the elements it's way too long. In assembly it
would take way less time than that, because I could move the reference value
in one of the CPU's register and leave it there as long as my loop runs and
iterate directly in the byte() to get 2 bytes at a time.


I think that using a MemoryStream and a BinaryReader is adding a lot of
overhead. Try the following code (C#, but I'm sure you can convert it
to VB.NET without too much hassle):

using System;

class Test
{
const int Iterations = 1000;
const int Size = 100000;

static void Main()
{
byte[] array = new byte[Size];

Random rng = new Random();

rng.NextBytes(array);

ushort threshold = (ushort)rng.Next(ushort.MaxValue);

DateTime start = DateTime.Now;
int counter=0;
for (int i=0; i < Iterations; i++)
{
for (int j=0; j < array.Length; j += 2)
{
int value = array[j] << 8 + array[j+1];
if (value > threshold)
{
counter++;
}
}
}
DateTime end = DateTime.Now;

Console.WriteLine ("Counter: {0}", counter);
Console.WriteLine ("Time taken: {0}", end-start);
}
}

On my computer, that takes about 6 seconds for *10,000* iterations (of
all 50,000 shorts). That means that if you call it 10 times a second,
it would still only take about 6ms of each second.

The important line is:

int value = (array[j] << 8) + array[j+1];

I don't know what the shift operators are in VB.NET, but that's the way
I'd go. (You may need to reverse which byte is shifted, of course -
that depends on the endianness of your data.)

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too
Feb 20 '06 #5
Hello,

Have you tried using Buffer.BlockCopy?

I would create an Int16 (Short) array that was long enough to hold all the 2-byte pairs in the byte array and use Buffer.BlockCopy
to just copy those bytes into the Int16 array directly. Then loop through the Int16 array instead of using the
MemoryStream/BinaryReader combination. I would think that would be faster.

Is that something that would work?

Kelly
"ThunderMusic" <NOdanlatSPAM@hotmaildotcom> wrote in message news:%2******************@TK2MSFTNGP14.phx.gbl...
Hi,
I need to optimize a close loop. Usually I would use assembly, but I don't event know if it's available to VB.NET. I'll explain
the case and maybe some of you will be able to advise me.

I have a byte() (byte array) containing about 100,000 elements (a bit less, but always is around 80,000-95,000). I need to take
the data from it as int16 and compare the int16 to a reference value

for now, I'm using a MemoryStream created from the byte(), a BinaryReader that reads from the MemoryStream (ReadInt16) and then
compare the int16 to a reference value and return false if the int16 is greater than the reference value. if all the values are
lower than the reference value, then the function returns true. If it returns after the first loop or so, it's ok, but if it runs
through all the elements it's way too long. In assembly it would take way less time than that, because I could move the reference
value in one of the CPU's register and leave it there as long as my loop runs and iterate directly in the byte() to get 2 bytes at
a time.

In VB.NET it's a function that stands in about 10 lines of code (maybe even lower), but it takes up to 50% of the CPU (when looked
in the task manager) which is way too much because it runs very often. When it does not run (many other things are running in the
app), the app takes about 1%-2% of the CPU, when this close loop starts being called, the app get's to 30%-50% of the CPU... it's
a bit excessive due to the fact that the function is called about 8-10 times a second.

thanks for your help

ThunderMusic

Feb 20 '06 #6
Kelly Ethridge <ke***@kellyethridge.com> wrote:
Have you tried using Buffer.BlockCopy?

I would create an Int16 (Short) array that was long enough to hold
all the 2-byte pairs in the byte array and use Buffer.BlockCopy to
just copy those bytes into the Int16 array directly. Then loop
through the Int16 array instead of using the
MemoryStream/BinaryReader combination. I would think that would be
faster.

Is that something that would work?


I've just tried that, and it's about twice as fast as my "manual
shifting" solution - at least if the ushort array can be reused
(repopulated, but not recreated). Oddly enough, I'd looked at Buffer
but not worked out the best way of using it.

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too
Feb 20 '06 #7
Ya, there's always a catch.

"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote in message news:MP************************@msnews.microsoft.c om...
Kelly Ethridge <ke***@kellyethridge.com> wrote:
Have you tried using Buffer.BlockCopy?

I would create an Int16 (Short) array that was long enough to hold
all the 2-byte pairs in the byte array and use Buffer.BlockCopy to
just copy those bytes into the Int16 array directly. Then loop
through the Int16 array instead of using the
MemoryStream/BinaryReader combination. I would think that would be
faster.

Is that something that would work?


I've just tried that, and it's about twice as fast as my "manual
shifting" solution - at least if the ushort array can be reused
(repopulated, but not recreated). Oddly enough, I'd looked at Buffer
but not worked out the best way of using it.

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too

Feb 20 '06 #8
use pointers !

byte[] array;
byte *pbyte = &array[0];
short* pshort = (short*)pbyte;

--
Regards,
Lloyd Dupont

NovaMind development team
NovaMind Software
Mind Mapping Software
<www.nova-mind.com>
"ThunderMusic" <NOdanlatSPAM@hotmaildotcom> wrote in message
news:Ou**************@TK2MSFTNGP14.phx.gbl...

"Mattias Sjögren" <ma********************@mvps.org> wrote in message
news:u%****************@tk2msftngp13.phx.gbl...

FYI, there's a group dedicated to performance issues;
microsoft.public.dotnet.framework.performance


thanks a lot, I didn't know because it's the first time I have a real
performance issue, so I'll use a profiler (as advised) and try posting
there. Thanks a lot.

ThunderMusic

Feb 21 '06 #9
Thanks a lot, I'll try both your solutions and give you feedback on how
well/fast it worked.

Thanks

ThunderMusic

"Kelly Ethridge" <ke***@kellyethridge.com> wrote in message
news:eM**************@TK2MSFTNGP11.phx.gbl...
Ya, there's always a catch.

"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote in message
news:MP************************@msnews.microsoft.c om...
Kelly Ethridge <ke***@kellyethridge.com> wrote:
Have you tried using Buffer.BlockCopy?

I would create an Int16 (Short) array that was long enough to hold
all the 2-byte pairs in the byte array and use Buffer.BlockCopy to
just copy those bytes into the Int16 array directly. Then loop
through the Int16 array instead of using the
MemoryStream/BinaryReader combination. I would think that would be
faster.

Is that something that would work?


I've just tried that, and it's about twice as fast as my "manual
shifting" solution - at least if the ushort array can be reused
(repopulated, but not recreated). Oddly enough, I'd looked at Buffer
but not worked out the best way of using it.

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too


Feb 22 '06 #10
ok, I tried the Buffer.BlockCopy solution, and it did work ultra fine... in
fact, when the method is run, the cpu does not even go up a bit, not even by
1%, it stays constant... my whole app is taking between 0% and 2% of CPU,
and before, with the MemoryStream and BinaryReader, it was taking up to 50%
of the CPU. Now it's totally seemless when the loop runs.

Thanks a lot

ThunderMusic
"ThunderMusic" <NOdanlatSPAM@hotmaildotcom> wrote in message
news:%2*****************@TK2MSFTNGP11.phx.gbl...
Thanks a lot, I'll try both your solutions and give you feedback on how
well/fast it worked.

Thanks

ThunderMusic

"Kelly Ethridge" <ke***@kellyethridge.com> wrote in message
news:eM**************@TK2MSFTNGP11.phx.gbl...
Ya, there's always a catch.

"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote in message
news:MP************************@msnews.microsoft.c om...
Kelly Ethridge <ke***@kellyethridge.com> wrote:
Have you tried using Buffer.BlockCopy?

I would create an Int16 (Short) array that was long enough to hold
all the 2-byte pairs in the byte array and use Buffer.BlockCopy to
just copy those bytes into the Int16 array directly. Then loop
through the Int16 array instead of using the
MemoryStream/BinaryReader combination. I would think that would be
faster.

Is that something that would work?

I've just tried that, and it's about twice as fast as my "manual
shifting" solution - at least if the ushort array can be reused
(repopulated, but not recreated). Oddly enough, I'd looked at Buffer
but not worked out the best way of using it.

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too



Feb 23 '06 #11

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

4
by: josef angermeier | last post by:
i wrote a display driver for a lcd segment display which doesnt recognize ascii character so that each character of an output string needs to be converted byte by byte by looking in a const...
3
by: Carl | last post by:
I do a project using C# and C++ .NET and have some functionality to convert imperial to metric units and vice versa. In VC6 I just used a simple header file with some constants (e.g. const...
3
by: Nick L. | last post by:
All, This is a general question regarding how, and if, compiler optimization techniques affect the general concept of being able to update a component of an application without requiring a...
14
by: joshc | last post by:
I'm writing some C to be used in an embedded environment and the code needs to be optimized. I have a question about optimizing compilers in general. I'm using GCC for the workstation and Diab...
24
by: Kunal | last post by:
Hello, I need help in removing if ..else conditions inside for loops. I have used the following method but I am not sure whether it has actually helped. Below is an example to illustrate what I...
21
by: mjbackues at yahoo | last post by:
Hello. I'm having a problem with the Visual Studio .net (2003) C++ speed optimization, and hope someone can suggest a workaround. My project includes many C++ files, most of which work fine...
12
by: rodneys | last post by:
Hi, please take a look to this sample code: class MyClass { private: static int length ; public: static void setLength(int newLength) ; void do() ;
5
by: Steve | last post by:
Hi, I am sitting down to design our next set of internal apps. I would like to approach this in a way that would allow me to break logical parts of the application that handle specific tasks...
10
by: SzH | last post by:
The code below demonstrates that the copy constructor of moo is not called on the first line of main. In spite of this, g++ (version 4.1.2) refuses to compile it if I make the copy constructor...
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows...
0
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new...
0
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.