...structured programming. While technically better on several levels, it does however represent an INCREASE in application development time. (decrease in productivity)
Who says? I'm pretty sure you will not find any evidence to back up that suggestion. Needless to say I totally disagree. I'm sure most programmers would also.
You guys are all mostly professional programmers, so you no longer see it from a novice perspective.
Perhaps. But I remember my first introduction to programming, in BASIC, as a teenager pretty well. Exciting times. It was rare to get your hands on a computer back then. Luckily they taught us assembler at the same time. Two years later I taught myself ALGOL as best I could. What a revelation. And a relief!
When the subject of 'retro Basic' comes up, someone will inevitably make the comment, "Yeah why don't we return to punch cards and magnetic memory too!" This is incorrect logic.
I would not say that is incorrect logic. I suspect it is sarcasm. They are taking the pee.
...worker productivity (and therefore per capita GDP) has actually peaked a couple decades ago.
That seems very unlikely as well. I'd love to see some evidence to back that up. A quick google turns up hundreds of graphs that show GDP rising since forever. Give or take a few dips here and there. But that is a topic for another thread.
All the bliss you seek is there, without the crippling absence of Goto.
Since being tortured with BASIC as a teenager I have only ever used one GOTO (And been able to justify it to our QA team). Far from being crippling getting away from GOTO is liberating.
I'm beginning to wonder if it's not so much that pbasic is so much easier than Spin but rather that the stuff that is built into pbasic that I would really consider the "runtime library" in a language like C makes it "one stop shopping". You have stuff like SERIN, SEROUT, etc and don't have to go rummaging through OBEX to find what you need. Maybe Spin would be easier to use if there was a way to easily add some equivalent objects without having to resort to asking questions on the forum and searching through OBEX. I guess that is what the "Parallax Gold Objects" were supposed to achieve but I don't think that effort really ever got off the ground. So, my claim is that it's the library support more than the language itself that makes pbasic easier for some. Of course, I suppose some will claim that things like SERIN are part of the pbasic language and no part of a library.
OT Seems this thread is continuing on the premise that it will be split by the moderators. Personally I don't think the OT section belongs in the P2 section as it applies to both P2& P2.
I'm not sure this discussion about pbasic on the Propeller is even off topic. Wasn't the original post about why Parallax doesn't support pbasic on the Propeller?
I'm beginning to wonder if it's not so much that pbasic is so much easier than Spin but rather that the stuff that is built into pbasic that I would really consider the "runtime library" in a language like C makes it "one stop shopping". You have stuff like SERIN, SEROUT, etc and don't have to go rummaging through OBEX to find what you need. Maybe Spin would be easier to use if there was a way to easily add some equivalent objects without having to resort to asking questions on the forum and searching through OBEX. I guess that is what the "Parallax Gold Objects" were supposed to achieve but I don't think that effort really ever got off the ground. So, my claim is that it's the library support more than the language itself that makes pbasic easier for some. Of course, I suppose some will claim that things like SERIN are part of the pbasic language and no part of a library.
You have probably hit the nail on the head with that observation, as this is what I see too. Glancing over the PBASIC "instruction set" I see macro extensions to the language, something that happens automatically with Forth systems where those extended library functions become part of the language, except in PBASIC's case it as been formalized and stamped into the spec.
But I do like the simplicity of some of those functions although they obviously have limitations but I have used SERIN and SEROUT in similar fashion too. Just pass it the pin number and baud rate and it is that easy whereas in Spin I think everyone reaches for a full-duplex object each time. If a language had easy to use functions like that built-in yet still allowed for faster and more powerful operations then it might be called PBASIC++
"top-down" ? No. Define your primitives first, so they don't get trapped by expectations from "above."
I used to worry about this top-down thing a lot in the early days. I found myself working on huge projects. A lot of people and millions in investment, over years, in software and hardware development. We would start at the top, with context diagrams and such, then do the prescribed "divide and conquer". After months of that we might actually start writing code.
I found myself wondering: How on Earth can anyone be sure this is going to work? How do we know we can actually create all those parts that have been pushed down to the lowest levels of design? I would imagine a hypothetical project that requires a Fourier transform, perhaps after years of effort you find the project fails because your Fourier Transform is so slow.
Same on the hardware side. A huge system gets specified. Then broken down into modules, racks, circuit boards etc. None of which exists when you start!
I think I came to the conclusion that it was all a bit of a sham. Just going through the motions. Those guys that had been in the business for decades and knew the technology inside out already knew what those lower level details would look like. Or at least they knew enough to be confident that the parts could be made. Subsystems and techniques had been developed in the lab and prototyped in some form years before. None of which was immediately obvious to this green horn.
I think you are right. Cogs should be cores and so on.
Certainly when I stumbled across the Prop all that talk of COGs and HUB off putting. Had the thing been described in terms we are used to I may have taken the Prop seriously a year or so before.
Like @Heater. said "In all of programming there is nothing but "sequence", "selection" and "iteration".
Actually I think I forgot something: "parallel". So we have at the lowest level of programming:
Sequence: "Do this, then to that, then do the other."
Selection: "If some condition is met do this otherwise do the other."
Iteration: "Do this repeatedly. (Or do this to these items)"
Parallel: "Do this and that and the other at the same time."
I'm not totally sure parallel belongs on the list, after all given a fast enough sequential machine one would not need to think about doing things in parallel.
Except perhaps "parallel" is a required conceptual primitive in cases like: "Wait for this event, that even and the other event, at the same time. When on of them happens do something"
But that brings us to another conceptual primitive "time". I only know of one programming language that has a concept of time built into it's syntax.
Language like Occam had the concept of "parallel" in the very syntax. One actually had to write "SEQ" to introduce sequential statements. One could write PAR to introduce statements that could be executed in parallel.
Javascript has the "events" case covered nicely. Baked into it's very being.
Sometimes I have thought that Spin could do with having a PAR construct in it's syntax. Rather than have it bolted on as a messy builtin function, cogstart.
Maybe because ordinary folks and even professionals find it useful. I remember my first intro to Basic in the real world - HP Instrument Basic that we used to troubleshoot the B1-B bomber's wiring and comm system.
Great stuff. I once worked in Marconi Avionics. I was amazed to find they had a BBC micro-computer built into a test rig for some Airbus flight controller. I'm pretty sure that was programmed in BBC BASIC. That was years after the BEEB had faded into obscurity.
Every CPU has a GOTO and GOSUB, they are usually called JMP and CALL. These instructions are "basic" instructions that every CPU needs
Just for the sake of argument I'm going to, err.., argue with that.
A CPU does not need JMP and CALL. Assuming one has access to the program counter one can just MOV new addresses into it and BOOM you are somewhere else in the program. Subroutine CALL and return can of course be synthesized similarly.
Rather that being "basic" instructions that every CPU needs they are rather higher level constructs. As are GOTO and GOSUB.
@Heater - You and I and many know that JMP and CALL are "move" operations, after all, everything is in a CPU, move this to there, to the ALU, move it from there etc. The Prop has a JMP and a CALL/JMPRET instruction and on the Prop the PC is not a general purpose register either, although that might be good if it were.
I think though that you are suffering from forumitis and getting overly pedantic about this, time to go and get some air, open a good bottle of wine, and enjoy!
btw, looking at the video I think if the Prop had mov'es like that it would be an x86
They also discussed macros, oh if only the Spin tool supported macros.
btw, looking at the video I think if the Prop had mov'es like that it would be an x86
They also discussed macros, oh if only the Spin tool supported macros.
IIRC macros have been asked for at least once before
Actually regularly for the past 10 years! And it's fallen on deaf ears!!!
You are right Peter. "forumitis". Pendantic is my middle name:)
"time to go and get some air". What? You know how cold it is out there? And dark.
"open a good bottle of wine, and enjoy" That's a better idea. Except that means going out there to get it. Hmm...there might be a beer at the back of the fridge somewhere....
Perhaps I should get down to writing that emulator for the Single Instruction Computer (SIC) I have been dreaming about. Only one instruction, SUBLEQ, subtract and branch if less or equal....
The logic on every CPU I have ever seen executes instructions by moving data between registers, so in that sense I agree with what you say. OTOH when the end result is that program ends up executing code that is stored at a location other than the next sequential location it is far better IMO to name them JMP or CALL than have a program consist of only MOV reg1, reg2, etc.
Since being tortured with BASIC as a teenager I have only ever used one GOTO (And been able to justify it to our QA team). Far from being crippling getting away from GOTO is liberating.
Over THIRTY YEARS ago, I began programming with MS QuickBASIC v2.0.
One can take any old BASICA/GW-BASIC (interpreter) code and run it without modification in QB. Line numbers, GOTOs, not a problem. It just runs a heck of a lot quicker.
However, it was also possible to avoid the use of both line numbers and GOTO, which for my own code, is what I preferred to do.
Bugatti Veyron is only an evolution of the Model T...Both are still just cars.
Thinking about it, the only time I remember using GOTO is right now in PropBASIC. Not because I don't have an option but because it generates the most efficient PASM output. If it ever bothers me, I can directly replace it with a PASM jmp.
"Liberating" for me was QuickBASIC 4.5 which is a threaded p-code interpreter. Runs code at compiled speeds but my code development cycle suddenly became Edit/Run whereas my competitors were still doing the Edit/Compile/Link/Locate/Run routine.
BASIC put me in business, 30 years ago, at a time when I was still trying to figure out what all these data types were for. Always been my secret weapon and still is.
I've never understood why PBASIC wasn't supported on the Prop from the beginning. This would have allowed Basic Stamp users to program the Prop without having to learn a whole new language. As I mentioned in an earlier post in this thread, it should be fairly easy to write a PBASIC bytecode interpreter for the Prop. Mike Green's response was the Basic Stamp bytecodes are proprietary, and Parallax has never posted documentation on them.
Maybe it's time for Parallax to open up the Basic Stamp. Actually, now that I think about it, Parallax may have purposely decided not to support PBASIC on the Prop in fear that the bytecode interpreter would be reverse engineered. They might have been concerned that someone else would build Basic Stamp modules and compete against them.
My post was actually related directly to the OP of the "Why..Oh..Why" thread. I guess because I mentioned the word "Basic" it got moved into this thread instead.
I'm beginning to wonder if it's not so much that pbasic is so much easier than Spin but rather that the stuff that is built into pbasic that I would really consider the "runtime library" in a language like C makes it "one stop shopping". You have stuff like SERIN, SEROUT, etc and don't have to go rummaging through OBEX to find what you need. Maybe Spin would be easier to use if there was a way to easily add some equivalent objects without having to resort to asking questions on the forum and searching through OBEX. I guess that is what the "Parallax Gold Objects" were supposed to achieve but I don't think that effort really ever got off the ground. So, my claim is that it's the library support more than the language itself that makes pbasic easier for some. Of course, I suppose some will claim that things like SERIN are part of the pbasic language and no part of a library.
Exactly, looking at items like the loosely named PBASIC.PWM (which seems to actually be a novel Tri-state-burst-PDM), those are less language keywords, and more runtime.
Surely tho, a smarter Spin that linked only used objects, could have a PBASIC runtime, that could match params and (where possible) operation of PBASIC ?
"Parallax Gold Objects" is far too loose a name, a more focused name is needed, as is unused code removal.
... I think it is possible to have PBASIC existing in some form on the Prop but rather than a "dead" source code that compiles to bytecode we could have it live and interactive on the Prop. But it wouldn't make any sense though to cripple this interactive PBASIC just for compatibility sake since the eight 32-bit core Prop is a far more capable MCU than the 8-bit PIC variants ever were. So I could overlay Tachyon with a modified PBASIC syntax so that it compiles in much the same way Tachyon does with full access to everything or I could write a preprocessor to take PBASIC source along with syntax checking etc to generate the modified PBASIC syntax for the user. The modified PBASIC syntax would be the initial way I could get it to work and then I could add the preprocessor on top of it. I could even get this to be standalone too with VGA and SD and a PS/2 keyboard. BTW, the speed of this PBASIC would be very fast and some of the hardware specific words such as PWM and SERIN/SEROUT could benefit from running continuously in other cogs.
Interesting idea.
For BASICS, I was musing about a simple preprocessor that is not byte-code level, but more a direct textual compressor/download. ie keywords are packed to shorter and params are sent in ~binary, not ascii.
What you suggest, is that on steroids...
Expanding on this...
If you dedicate a fast link for the download, the BASIC kernal can report back live line numbers, and so give a source-level trace.
I've been testing a new CP2102N, and find that can burst at 4MBd (512 byte buffers each way).
If you want duplex 4MBd, you need handshake enabled and there it can sustain an average of around 260kBytes/sec each way.
Suppose, say a 32b or 4 byte trace payload is used, at 4MBd that needs ~ 10us to report.
At the modest BS2 speeds of 4000 lines/sec that is ~ 4% overhead if the same COG manages the report, much less if a second COG handles the reporting.
A second COG for debug trace link manage, could track live 20,000 lines/sec, and report line# and a few 16b watch vars to an IDE.
No matter how much I harp on about this awesome compiler/translator, the point doesn't seem to get across that the reason I use it is not because it is extremely easy to code with....it's because it generates PASM code with zero overhead.
I have no problem using SPIN but it just isn't quick enough for my needs.
I'm beginning to wonder if it's not so much that pbasic is so much easier than Spin but rather that the stuff that is built into pbasic that I would really consider the "runtime library" in a language like C makes it "one stop shopping".
The SimpleTools library for PropGCC does these things, and arguably makes it easier to use than Spin. It also has formatted printing and better handling of string output, which is something I always found comparatively painful in Spin.
As a point of fact, the Propeller does not have a CALL, JMP, or RET instruction. They're all just JMPRETs with the option to write the result or not. Neither implementation (JMPRET or JMPRET nr) is equivalent to a GOSUB or CALL, since there's no return stack. Moreover the code is not reentrant, since the object code itself is "corrupted." Still, though, it's an elegant system that works well if you avoid recursion or take extra steps to accommodate it.
No matter how much I harp on about this awesome compiler/translator, the point doesn't seem to get across that the reason I use it is not because it is extremely easy to code with....it's because it generates PASM code with zero overhead.
I have no problem using SPIN but it just isn't quick enough for my needs.
Have you ever used a macro assembler? PropBASIC is not that. However I just wonder how large your programs are because you keep saying that it generates PASM code with zero overhead, which is true for any tiny bit of code that can fit into an absolute maximum of 496 PASM instructions in a cog, less though as some need to be registers. Doesn't it generate LMM code which requires a runtime interpreter and runs about ten times slower than PASM yet has the same memory overhead? Could you fit a FAT32 filesystem into a Prop and still have room for an application?
My applications include FAT32 and Ethernet servers so there is no way in the world that it could ever run in a cog or LMM or even CMM, and XMM would be way too slow.
@PhiPI - still, the Prop has a JMP and a CALL instruction as like so many CPUs I have dealt with these instructions are operations by another name.
Not in the normal sense, as it compiles BASIC source code, and outputs PASM.
Usual meaning of Macro Assembler is SW that reads ASM source files and can support Macros.
Most have native opcode for one processor included, and others can be added using the macros.
fasmg is a little unusual, in that it is a pure macro language, assembler use focused, and even x86 is done with macros.
The Macro ability of fasmg, is well above most assemblers that add macros.
No matter how much I harp on about this awesome compiler/translator, the point doesn't seem to get across that the reason I use it is not because it is extremely easy to code with....it's because it generates PASM code with zero overhead.
That's a classic Compiler pathway. Some compilers also include an Assembler-step, somewhat hidden from users.
I have no problem using SPIN but it just isn't quick enough for my needs.
You could look at Spin2cpp, as that can also output P1 PASM and P2 PASM
- ie operationally close to PropBASIC, but I think PropBASIC is more mature, and probably generates better code.
In the 8-bit computer days, BASIC was commonly expanded using the & command.
Typically a Machine Language program would intercept the "BASIC Vector", so it could first check if any & commands were being used.
There were also BASIC cartridges on some computers and some later models added more commands to their BASIC.
MS-DOS QBASIC was the greatest thing that Microsoft ever did. Even today I can take an old 8-bit BASIC program and after removing the machine specific commands get it to run on a PC.
VB is something else entirely!
Would refering to Spin as SpinBASIC get any converts?
You could look at Spin2cpp, as that can also output P1 PASM and P2 PASM
- ie operationally close to PropBASIC, but I think PropBASIC is more mature, and probably generates better code.
You might want to check that. The last I heard PropBASIC just did a simple unoptimized translation into PASM. I think Bean said it was pretty much one-to-one. I believe Eric has at least some optimization in his PASM generator and going through GCC gives you all of its optimizations.
Comments
You have probably hit the nail on the head with that observation, as this is what I see too. Glancing over the PBASIC "instruction set" I see macro extensions to the language, something that happens automatically with Forth systems where those extended library functions become part of the language, except in PBASIC's case it as been formalized and stamped into the spec.
But I do like the simplicity of some of those functions although they obviously have limitations but I have used SERIN and SEROUT in similar fashion too. Just pass it the pin number and baud rate and it is that easy whereas in Spin I think everyone reaches for a full-duplex object each time. If a language had easy to use functions like that built-in yet still allowed for faster and more powerful operations then it might be called PBASIC++
I found myself wondering: How on Earth can anyone be sure this is going to work? How do we know we can actually create all those parts that have been pushed down to the lowest levels of design? I would imagine a hypothetical project that requires a Fourier transform, perhaps after years of effort you find the project fails because your Fourier Transform is so slow.
Same on the hardware side. A huge system gets specified. Then broken down into modules, racks, circuit boards etc. None of which exists when you start!
I think I came to the conclusion that it was all a bit of a sham. Just going through the motions. Those guys that had been in the business for decades and knew the technology inside out already knew what those lower level details would look like. Or at least they knew enough to be confident that the parts could be made. Subsystems and techniques had been developed in the lab and prototyped in some form years before. None of which was immediately obvious to this green horn.
10 PRINT "HELLO"
20 GOTO 10
There is nothing there that you don't need. No distracting baggage like # includes and main() or whatever other languages require.
However it all goes down hill soon after that
I think you are right. Cogs should be cores and so on.
Certainly when I stumbled across the Prop all that talk of COGs and HUB off putting. Had the thing been described in terms we are used to I may have taken the Prop seriously a year or so before.
Sequence: "Do this, then to that, then do the other."
Selection: "If some condition is met do this otherwise do the other."
Iteration: "Do this repeatedly. (Or do this to these items)"
Parallel: "Do this and that and the other at the same time."
I'm not totally sure parallel belongs on the list, after all given a fast enough sequential machine one would not need to think about doing things in parallel.
Except perhaps "parallel" is a required conceptual primitive in cases like: "Wait for this event, that even and the other event, at the same time. When on of them happens do something"
But that brings us to another conceptual primitive "time". I only know of one programming language that has a concept of time built into it's syntax.
Language like Occam had the concept of "parallel" in the very syntax. One actually had to write "SEQ" to introduce sequential statements. One could write PAR to introduce statements that could be executed in parallel.
Javascript has the "events" case covered nicely. Baked into it's very being.
Sometimes I have thought that Spin could do with having a PAR construct in it's syntax. Rather than have it bolted on as a messy builtin function, cogstart.
A CPU does not need JMP and CALL. Assuming one has access to the program counter one can just MOV new addresses into it and BOOM you are somewhere else in the program. Subroutine CALL and return can of course be synthesized similarly.
Rather that being "basic" instructions that every CPU needs they are rather higher level constructs. As are GOTO and GOSUB.
By the way, did you know that on x86 you can write any program using only MOV instructions? https://github.com/xoreaxeaxeax/movfuscator Yep, MOV is Turing complete on x86.
I think though that you are suffering from forumitis and getting overly pedantic about this, time to go and get some air, open a good bottle of wine, and enjoy!
btw, looking at the video I think if the Prop had mov'es like that it would be an x86
They also discussed macros, oh if only the Spin tool supported macros.
IIRC macros have been asked for at least once before
Actually regularly for the past 10 years! And it's fallen on deaf ears!!!
"time to go and get some air". What? You know how cold it is out there? And dark.
"open a good bottle of wine, and enjoy" That's a better idea. Except that means going out there to get it. Hmm...there might be a beer at the back of the fridge somewhere....
Perhaps I should get down to writing that emulator for the Single Instruction Computer (SIC) I have been dreaming about. Only one instruction, SUBLEQ, subtract and branch if less or equal....
The logic on every CPU I have ever seen executes instructions by moving data between registers, so in that sense I agree with what you say. OTOH when the end result is that program ends up executing code that is stored at a location other than the next sequential location it is far better IMO to name them JMP or CALL than have a program consist of only MOV reg1, reg2, etc.
Over THIRTY YEARS ago, I began programming with MS QuickBASIC v2.0.
One can take any old BASICA/GW-BASIC (interpreter) code and run it without modification in QB. Line numbers, GOTOs, not a problem. It just runs a heck of a lot quicker.
However, it was also possible to avoid the use of both line numbers and GOTO, which for my own code, is what I preferred to do.
Bugatti Veyron is only an evolution of the Model T...Both are still just cars.
Thinking about it, the only time I remember using GOTO is right now in PropBASIC. Not because I don't have an option but because it generates the most efficient PASM output. If it ever bothers me, I can directly replace it with a PASM jmp.
"Liberating" for me was QuickBASIC 4.5 which is a threaded p-code interpreter. Runs code at compiled speeds but my code development cycle suddenly became Edit/Run whereas my competitors were still doing the Edit/Compile/Link/Locate/Run routine.
BASIC put me in business, 30 years ago, at a time when I was still trying to figure out what all these data types were for. Always been my secret weapon and still is.
Moderators will remove anything not a direct comment to the OP, or in response to his remarks.
My post was actually related directly to the OP of the "Why..Oh..Why" thread. I guess because I mentioned the word "Basic" it got moved into this thread instead.
I cannot re-merge the comment, though you could re-post it to the correct discussion and have me remove it from this one.
Exactly, looking at items like the loosely named PBASIC.PWM (which seems to actually be a novel Tri-state-burst-PDM), those are less language keywords, and more runtime.
Surely tho, a smarter Spin that linked only used objects, could have a PBASIC runtime, that could match params and (where possible) operation of PBASIC ?
"Parallax Gold Objects" is far too loose a name, a more focused name is needed, as is unused code removal.
Very Smart Macros was one reason I took a look at fasmg, for P1/P2 assembler.
Looks to be workable, from the tests I did.
Interesting idea.
For BASICS, I was musing about a simple preprocessor that is not byte-code level, but more a direct textual compressor/download. ie keywords are packed to shorter and params are sent in ~binary, not ascii.
What you suggest, is that on steroids...
Expanding on this...
If you dedicate a fast link for the download, the BASIC kernal can report back live line numbers, and so give a source-level trace.
I've been testing a new CP2102N, and find that can burst at 4MBd (512 byte buffers each way).
If you want duplex 4MBd, you need handshake enabled and there it can sustain an average of around 260kBytes/sec each way.
Suppose, say a 32b or 4 byte trace payload is used, at 4MBd that needs ~ 10us to report.
At the modest BS2 speeds of 4000 lines/sec that is ~ 4% overhead if the same COG manages the report, much less if a second COG handles the reporting.
A second COG for debug trace link manage, could track live 20,000 lines/sec, and report line# and a few 16b watch vars to an IDE.
No matter how much I harp on about this awesome compiler/translator, the point doesn't seem to get across that the reason I use it is not because it is extremely easy to code with....it's because it generates PASM code with zero overhead.
I have no problem using SPIN but it just isn't quick enough for my needs.
The SimpleTools library for PropGCC does these things, and arguably makes it easier to use than Spin. It also has formatted printing and better handling of string output, which is something I always found comparatively painful in Spin.
-Phil
Have you ever used a macro assembler? PropBASIC is not that. However I just wonder how large your programs are because you keep saying that it generates PASM code with zero overhead, which is true for any tiny bit of code that can fit into an absolute maximum of 496 PASM instructions in a cog, less though as some need to be registers. Doesn't it generate LMM code which requires a runtime interpreter and runs about ten times slower than PASM yet has the same memory overhead? Could you fit a FAT32 filesystem into a Prop and still have room for an application?
My applications include FAT32 and Ethernet servers so there is no way in the world that it could ever run in a cog or LMM or even CMM, and XMM would be way too slow.
@PhiPI - still, the Prop has a JMP and a CALL instruction as like so many CPUs I have dealt with these instructions are operations by another name.
Usual meaning of Macro Assembler is SW that reads ASM source files and can support Macros.
Most have native opcode for one processor included, and others can be added using the macros.
fasmg is a little unusual, in that it is a pure macro language, assembler use focused, and even x86 is done with macros.
The Macro ability of fasmg, is well above most assemblers that add macros.
That's a classic Compiler pathway. Some compilers also include an Assembler-step, somewhat hidden from users.
You could look at Spin2cpp, as that can also output P1 PASM and P2 PASM
- ie operationally close to PropBASIC, but I think PropBASIC is more mature, and probably generates better code.
Typically a Machine Language program would intercept the "BASIC Vector", so it could first check if any & commands were being used.
There were also BASIC cartridges on some computers and some later models added more commands to their BASIC.
MS-DOS QBASIC was the greatest thing that Microsoft ever did. Even today I can take an old 8-bit BASIC program and after removing the machine specific commands get it to run on a PC.
VB is something else entirely!
Would refering to Spin as SpinBASIC get any converts?