Talking about percentage, you can generate an integer number from 0 to 99 than subdivide your 100% into chunks of different sizes:
| 10 | 10 | 20 | 30 | 30 |
1 5 2 4 3
so if random is [0 10[ => 1; [10 20[ => 5; [20 40[ => 2 [40 70[ => 4 [70 100[ =>5
this means that you will get 1 and 5 with 10%, 2 with 20%, 3 and 4 with 30%.
This method can be stressed further as @zacharmarz correctly pointed out.
Whichever size you use for your uniform generation, you will arrive to run out resolution so you know that will be points in the curve that you will never reach. Let say that MAXRAND is 1000, you can't newer get results of the curve beween 123 and 124 for example. You can go further by doing another generation so you can subdivide the curve between 123 and 124 in 1000 pieces
here an example with MAXRAND = 6 (!!)

The orange comes from the first extraction and the dark cyan comes from the second one