Why prevents bitcoins from being sent from the testnet to mainnet?
Testnet and mainnet are two different blockchains, and their coins are incompatible.
A transaction takes outputs that already exist on the blockchain, and re-assign them as outputs to different addresses. Think of a blockchain as a database. Let's say testnet has outputs A, B, and C. They are in the testnet database. However, mainnet has never heard of these outputs. They simply don't exist in the mainnet database. Any transaction that is submitted to mainnet using A, B, or C will be immediately rejected. Likewise, if you submit the same transaction to testnet, then the transaction goes through...but it goes through on testnet. Mainnet is still none the wiser.