Attempting to improve Math.random() in browser - javascript

Looking for a little expert advice on this one, my knowledge of cryptography is cursory at best.
I'm wondering if this is a viable solution for generating cryptographically secure random numbers. More specifically I'm wondering if using Math.abs() or Math.sin() to clamp the number will reduce the randomness of the number I get from crypto.getRandomValues so much that it is no longer useful for encryption.
if(window.crypto && window.crypto.getRandomValues) {
Math.random = () => {
var array = new Uint32Array(1)
window.crypto.getRandomValues(array)
return Math.abs(Math.sin(array[0]))
}
}
console.log(Math.random())
jsfiddle: https://jsfiddle.net/mg7ftm7w/
note: I've only tested this snippet in Chrome. I don't think the window.crypto object is present in IE.

Related

Is there a JavaScript equivalent to numpy.linalg.pinv?

I'm trying to solve a linear system of equations that is overdetermined (Ax = B) given a matrix A generated by user input on a website with Javascript. In python I could just use numpy.linalg.pinv(A) to find the pseudoinverse of A and multiply that pseudo inverse with B to solve the system -- is there a JavaScript equivalent (library and/or piece of code) that could do this?
I tried using math.js; although it doesn't seem to have a pseudo inverse function, it has other matrix operations. I tried using
math.multiply(math.inv(math.multiply(math.transpose(A), A)), math.transpose(A))
to find the pseudo inverse but the matrix I got from multiplying the transpose of A with A was not invertible because the columns of A are apparently linearly dependent (I'm not very experienced with linear algebra but that's what I've gathered from some research online). However, numpy can still find a pseudo inverse even when the matrix A has linearly dependent columns (I tested the system with numpy) so that brings me back to the question of whether there's a way to replicate numpy's pseudo inverse function. And if not, is there some other solution to this problem?
Q : And if not, is there some other solution to this problem?
Yes, there is a way.
Implement distributed-processing workflow. Let JavaScript do its part and let numpy side do the work it is so smart at. Similar concept is common for many use-cases, where specialised tools solve parts of the problem and some workflow integration mediator "glues" the distributed parts together.
So, make JavaScript part equipped with ZeroMQ/zmq or nanomsg, communicate the A, B over the interconnect to a python-side, there numpy will make its best for the smart, vectorised number-crunching, and let the received results pass back to whatever next stage of the processing workflow.
ZeroMQ has for years smart tooling for very fast and efficient protocol-less { ipc:// | vmci:// } localhost interconnects, plus has similarly smart, yet non-local protocols for { tcp:// | udp:// | ... } datacentre interconnects, if your localhost resources would become prohibitively small for larger matrix sizes.
There are similar tools ready from nanomsg, yet you have to check for availability of JavaScript-side usable ports / wrappers.
The rest is just about squeezing out the maximum performance for any given volume of data and a requested cadence of the front-end / back-end transactions running.
Having used this architecture for a turn-around-time under ~ 80 [ms] just your imagination is your limit. Having also done some multi-TB linear algebra processing as fast as possible, more care will be necessary there, but the performance-motivated principles are the same.
I know it's been some time since this question was asked, but there are a few libraries for doing linear algebra in JS available now (2021), which I'll leave here for reference:
ml-matrix
eigen
linear-algebra-js
emlapack
linalg.js
Just to name a few. From your question it seems like you are trying to solve a least squares estimator:
If this is the case, most (all?) of the above libraries provide more robust / performant solutions compared to computing the pseudo-inverse, namely using LU/QR/SVD decompositions:
// Using ml-matrix
const { Matrix, solve } = require('ml-matrix');
var X = new Matrix([[1, 2, 3], [4, 5, 6], [7, 8, 9]]);
var y = Matrix.columnVector([8, 20, 32]);
var b = solve(X, y, (useSVD = true));
// Using linear algebra js
const { SparseMatrix, DenseMatrix } = require('linear-algebra');
// solve the linear system Ax = b, where A is a square sparse matrix
var X = SparseMatrix.identity(5, 5);
var y = DenseMatrix.ones(5, 1);
var lu = X.lu();
var b = lu.solveSquare(y);
However, if you really require calculating the pseudo-inverse, ml-matrix is the only library which supports this (as far as I know). In principle, Eigen supports this as well, but I haven't seen any JS port actually exposing this functionality yet.

Non-linear regression with errors in variables in JavaScript

I need a robust curve-fitting algorithm that would work in a browser. Namely I need it to be able to fit polynomial and trigonometric (and ideally all custom) functions, and it also has to account for errors in both variables.
I would like to use an existing library or rewrite an implementation written in a different but understandable language (pseudocode, Python, C#, C without much memory magic, etc.). Alternatively I could use a transpliter to JavaScript if it were possible. However I've searched for hours and haven't found any suitable JavaScript library, nor a straightforward implementation that I could crib.
I have found two pieces of software that can do what I want.
The first one is Gnuplot which is a utility written in C. It's open-source, but I found the code somewhat convoluted and the curve-fitting part was quite inter-dependent with other parts of the program, so I didn't manage to port it to JavaScript.
The second one is SciPy, a math library for Python. That would be an easy victory if the relevant part were actually written in Python. Which, sadly, is not the case, as instead it's a piece of old Fortran code modified, so that it can communicate with Python. The code was too difficult and archaic for me and Fortran-to-Javascript transpliters didn't work because of the Python-specific stuff in the code.
Do you know any project I could use? I know it's not going to be a “solve-all answer” but I will appreciate anything that will get me closer to the finish.
gnuplot can be transcoded via Emscripten to run as javascript in a browser. See live demonstration site gnuplot + emscripten.
The resulting javascript variant is not currently supported by the gnuplot project but the proof-of-principle demonstration is impressive.
Alglib.js will allow you to fit data data to an arbitrary function.
Go here for a complete example https://pterodactylus.github.io/Alglib.js/curve_fitting.html
<script type="module">
import {Alglib} from 'https://cdn.jsdelivr.net/gh/Pterodactylus/Alglib.js#master/Alglib-v1.1.0.js'
//import {Alglib} from '../Alglib-v1.1.0.js'
var f = function(a_n, x){
return a_n[3]*Math.pow(x, 3)+a_n[2]*Math.pow(x, 2)+a_n[1]*Math.pow(x, 1)+a_n[0];
}
let data = [[-3, 8], [1,3], [5,3], [9,8], [10,16]]
var fn1 = function(a){
let sum = 0
for (let i = 0; i < data.length; ++i) {
sum = sum + Math.pow(data[i][1] - f(a, data[i][0]), 2)
}
let sse = Math.sqrt(sum)
return sse
}
let solver = new Alglib()
solver.add_function(fn1) //Add the first equation to the solver.
solver.promise.then(function(result) {
var x_guess = [1,1,1,1] //Guess the initial values of the solution.
var s = solver.solve("min", x_guess) //Solve the equation
let x = solver.get_report()
solver.remove() //required to free the memory in C++
})
</script>

How to get some math errors in JavaScript

I'm doing some math in Node.js, and I've run into some situations in which a calculation that I would expect to give an error, such as division by 0 and the logarithm of 0, does not do so.
I've read the documentation and some other Q/As, and I understand that returning things like Infinity and -Infinity is normal behavior in Javascript. I'm not arguing for/against this.
I'm wondering, however, if there's a clever way to make JavaScript give me an error instead of continuing the calculations when this happens. The biggest issue is sometimes, an Infinity or -Infinity will get generated in the middle of a long and complex calculation, and that number will continue to be used, and eventually the overall calculation will simply return a normal number which is simply wrong. It's difficult to debug because we have no way of knowing right off the bat where the error happened, since no error is getting thrown and Infinity is an acceptable number in JS.
While the answer to Best way to prevent/handle divide by 0 in javascript provides an answer for specific, known cases where this might occur, I am seeking a catch-all solution for detecting when this might occur, rather than hunt down every case where it might occur or discover each case as I go.
The short answer is don't use javascript for any serious math. Javascript is fault-tolerant (which is why it has Infinity, -Infinity, -0, and NaN), but math isn't. Math is supposed to fail when you try impossible things.
As Gothdo has stated, creating custom functions for the behavior would work.
If you're doing math on more complicated objects (such as Points, or Vectors, or Spaces) that can be represented by a JSON object, there's a way to overload the vanilla operators.
http://www.2ality.com/2011/12/fake-operator-overloading.html
full source at
https://github.com/rauschma/op_overload
It's slightly tricky, and it's not really any more practical than just using functions, but it's kinda cool.
You can for example make a function divide that throws error if the result if the division is Infinity:
const divide = function(dividend, divisor) {
const result = dividend / divisor
if (Math.abs(result) === Infinity) {
throw new Error("Division by zero")
}
return result
}
Then in calculations, instead of using the division operator, use that function:
const fourDividedByTwo = divide(4, 2) // gives 2
const oneDividedByZero = divide(1, 0) // throws error

How to manage arguments

I apologise in advance if I'm too bad at using the search engine and this has already been answered. Please point me in the right direction in that case.
I've recently begun to use the arguments variable in functions, and now I need to slice it. Everywhere I look people are doing things like:
function getArguments(args, start) {
return Array.prototype.slice.call(args, start);
}
And according to MDN this is bad for performance:
You should not slice on arguments because it prevents optimizations in JavaScript engines (V8 for example).
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/arguments
Is there a reason why I don't see anyone doing things like this:
function getArguments(args, start) {
var i, p = 0;
var len = args.length;
var params = [];
for (i = start; i < len; ++i) {
params[p] = args[i];
p += 1;
}
return params;
}
You get the arguments you want, and no slicing is done. So from my point of view, you don't loose anything on this, well maybe it uses a little extra memory and is slightly slower, but not to the point where it really makes a difference, right?
Just wanted to know if my logic here is flawed.
Here is a discuss
and here is introduction
e.g. here uses the inline slice
It appears from the discussion that #Eason posted, (here) that the debate is in the "microptimization" category, ie: most of us will never hit those performance bumps because our code isn't being run through the kind of iterations needed to even appear on the radar.
Here's a good quote that sums it up:
Micro-optimizations like this are always going to be a trade-off
between the code's complexity/readability and its performance.
In many cases, the complexity/readability is more important. In this case, the
very slowest method that was tested netted a runtime of 4.3
microseconds. If you're writing a webservice and you're slicing args
two times per request and then doing 100 ms worth of other work, an
extra 0.0086 ms will not be noticeable and it's not worth the time or
the code pollution to optimize.
These optimizations are most helpful in really hot loops that you're hitting a gajillionty times. Use a
profiler to find your hot code, and optimize your hottest code first,
until the performance you've achieved is satisfactory.
I'm satisfied, and will use Array.prototype.slice.call() unless I detect a performance blip that points to that particular piece of code not hitting the V8 optimizer.

What is the fastest way to generate a random integer in javascript?

Normally this is how you get a random number in javascript.
Math.random();
However, this method seems to be inefficient when it comes to generating random integers.
Firstly, the random function has to generate a random decimal, like 0.1036098338663578, then it has to be multiplied to a suitable range (10.464593220502138). Finally, the floor function subtracts the decimals to produce the result (which in this case, 10).
var random_integer = Math.floor(Math.random()*101);
Is there a faster way to generate random integers in javascript?
Edit1:
I am using this for creating a canvas HTML5 game. The FPS is about 50, and my code is pretty optimized, apart from generating a random number.
This code is faster... to type.
var random_integer = Math.random()*101|0;
It won't work right for huge numbers though.
(and it doesn't run any faster, at least not in chrome.)
You could achieve a much faster speed during the game if you generate the random numbers beforehand, though.
for (var i=1e6, lookupTable=[]; i--;) {
lookupTable.push(Math.random()*101|0);
}
function lookup() {
return ++i >= lookupTable.length ? lookupTable[i=0] : lookupTable[i];
}
lookup will rotate through an array with a million random integers. It is much faster than calling random and floor (of course, there is a "loading time" penalty up front from generating the lookup table).
If you want to avoid floating point calculation then you can do that by writing your own pseudo random number generator. Here is a list of well known pseudo random number generators (PRNG). Linear congruential generator is the easiest one to implement and probably most effective in terms of performance too. However, you will need to understand the theory behind PRNGs well enough to write an effective one. That might not be worth of effort though. The JS implementation should be effective enough. At the end there is a high possibility that you will find Math.random() is running faster than your code.
i mostly use
var a = Math.floor(Math.random((number you'd like to be minimum, (number you'd like to be maximum) * (number you'd like to be maximum);
No, there is no easier or shorter way. You can create a function if you need to do it multiple times, though.
const getRandomInt = (base = 10) => {
return Math.floor(Math.random() * base)
}
Heres what I use:
function getRandomInt(max) {
return Math.floor(Math.random() * max);
}
An example of how this would be used would be
function getRandomInt(max) {
return Math.floor(Math.random() * max);
}
if(getRandomInt(420) == 69){
console.log("nice")
}
Your way is the right way to retrive a random integer in javascript, don't worry about performance it will run fast.
This is the shortest one-liner Random Number Generator code
rnd=(a,b)=>~~(Math.random()*(b-a))+a
How To Use: rnd(min,max)
Example : rnd(10,100)

Categories

Resources