06-05-2025, 03:38 PM
Your code is fine, it is SB that is slow.
In some ways that is the charm - reminding me of early days using ZX Spectrum where you had to code very carefully to be efficient.
It is mainly slow because it has a single type (Primitive) that is inernally checked and converted to required types, it also uses reflection to pass data. Internal data is stored in Dictionaries (e.g. Controls, Shapes, Images etc) that are indexed by a Primitie name, lookup is slow if there are lots of these. SB Arrays are especially slow since they are converted between string representations of Dictionaries internally. sVB uses pretty much the same compiler and command libarary with a few syntax changes. Arrays are usually the biggest culprit and extensions can be used to store data in Arrays and Lists.
For example if we look at the SB code for GraphicsWindow.DrawLine:
VerifyAccess does some checks that the GraphicsWindow is there
BeginInvoke runs the command as a delegate on the GraphicsWindow thread
drawingContext is created and appended to the current list of drawings made
DrawLine draws the line to the drawingContex
Close closes the context
AddRasterizeOperationToQueue looks at the size of the current series of drawing contexts in _mainDrawing and if ithere are more than 100, then it takes those 100 draw commands and redraws them to a bitmap that is then rendered to the background and _mainDrawing is reset ready for the next set of draw commands
If we look at GraphicsWindow.GetColorFromRGB:
The color is stored as a string "#RRGGBB" - every time this color is used it needs to be converted to the internal color type
Every If comparison has to first work out whether the variables should be treated as numbers or strings. In a modern language each variable has a specific type and the compiler won't let you do inappropriate things. In SB this is all done at runtime, so for example we can add a number to a string and get concatenation or addition depending on whether the string can be interpreted as a number. Checks for this are done all the time, every operation on data needs to check what the type of the data might actually be.
TextWindow.WriteLine("24.5"+2)
TextWindow.WriteLine("X24.5"+2)
In some ways that is the charm - reminding me of early days using ZX Spectrum where you had to code very carefully to be efficient.
It is mainly slow because it has a single type (Primitive) that is inernally checked and converted to required types, it also uses reflection to pass data. Internal data is stored in Dictionaries (e.g. Controls, Shapes, Images etc) that are indexed by a Primitie name, lookup is slow if there are lots of these. SB Arrays are especially slow since they are converted between string representations of Dictionaries internally. sVB uses pretty much the same compiler and command libarary with a few syntax changes. Arrays are usually the biggest culprit and extensions can be used to store data in Arrays and Lists.
For example if we look at the SB code for GraphicsWindow.DrawLine:
Code:
GraphicsWindow.VerifyAccess();
GraphicsWindow.BeginInvoke(delegate
{
DrawingContext drawingContext = GraphicsWindow._mainDrawing.Append();
drawingContext.DrawLine(GraphicsWindow._pen, new Point((double)x1, (double)y1), new Point((double)x2, (double)y2));
drawingContext.Close();
GraphicsWindow.AddRasterizeOperationToQueue();
});
VerifyAccess does some checks that the GraphicsWindow is there
BeginInvoke runs the command as a delegate on the GraphicsWindow thread
drawingContext is created and appended to the current list of drawings made
DrawLine draws the line to the drawingContex
Close closes the context
AddRasterizeOperationToQueue looks at the size of the current series of drawing contexts in _mainDrawing and if ithere are more than 100, then it takes those 100 draw commands and redraws them to a bitmap that is then rendered to the background and _mainDrawing is reset ready for the next set of draw commands
If we look at GraphicsWindow.GetColorFromRGB:
Code:
int num = Math.Abs(red % 256);
int num2 = Math.Abs(green % 256);
int num3 = Math.Abs(blue % 256);
return string.Format("#{0:X2}{1:X2}{2:X2}", num, num2, num3);
The color is stored as a string "#RRGGBB" - every time this color is used it needs to be converted to the internal color type
Every If comparison has to first work out whether the variables should be treated as numbers or strings. In a modern language each variable has a specific type and the compiler won't let you do inappropriate things. In SB this is all done at runtime, so for example we can add a number to a string and get concatenation or addition depending on whether the string can be interpreted as a number. Checks for this are done all the time, every operation on data needs to check what the type of the data might actually be.
TextWindow.WriteLine("24.5"+2)
TextWindow.WriteLine("X24.5"+2)