I'm beginner in deep learning, and trying to understand how algorithms works, writing them using JavaScript. Now I'm working on JavaScript implementation of conv2d like Tensorflow does, and misunderstand how to handle different count of filters, I have succeeded for one output filter and multiple output, but I'm confused how to produce operations with multiple filters input e.g. 32 -> 64
Here is example of code using ndarray
:
const outCount = 32 // count of inputs filters
const inCount = 1 // count of output features
const filterSize = 3
const stride = 1
const inShape = [1, 10, 10, outCount]
const outShape = [
1,
Math.ceil((inShape[1] - filterSize + 1) / stride),
Math.ceil((inShape[2] - filterSize + 1) / stride),
outCount
];
const filters = ndarray([], [filterSize, filterSize, inCount, outCount])
const conv2d = (input) => {
const result = ndarray(outShape)
// for each output feature
for (let fo = 0; fo < outCount; fo += 1) {
for (let x = 0; x < outShape[1]; x += 1) {
for (let y = 0; y < outShape[2]; y += 1) {
const fragment = ndarray([], [filterSize, filterSize]);
const filter = ndarray([], [filterSize, filterSize]);
// agregate fragment of image and filter
for (let fx = 0; fx < filterSize; fx += 1) {
for (let fy = 0; fy < filterSize; fy += 1) {
const dx = (x * stride) + fx;
const dy = (y * stride) + fy;
fragment.data.push(input.get(0, dx, dy, 0));
filter.data.push(filters.get(fx, fy, 0, fo));
}
}
// calc dot product of filter and image fragment
result.set(0, x, y, fo, dot(filter, fragment));
}
}
}
return result
}
For test I'm using a Tenforflow as a source of true and it algorithm works correct but with 1 -> N. But my question how to add a support of multiple filters in input value like N -> M.
Could someone explain how to modify this algorithm to make it more compatible with Tensorflow tf.nn.conv2d
A lot of thanks.
You would need to add another for loop. You didn't specify all of your input shapes and dimensions so it's actually kind of hard to write it exactly but it would look like this.
// agregate fragment of image and filter
for (let fx = 0; fx < filterSize; fx += 1) {
for (let fy = 0; fy < filterSize; fy += 1) {
//addition
for (let ch = 0; ch < input.get_channels) {
const dx = (x * stride) + fx;
const dy = (y * stride) + fy;
fragment.data.push(input.get(0, dx, dy, ch));
filter.data.push(filters.get(fx, fy, ch, fo));
}
}
}
Related
I want to check if a point lies within a specific polygon. The polygon is:
polygon= [ [-73.89632720118, 40.8515320489962],
[-73.8964878416508, 40.8512476593594],
[-73.8968799791431, 40.851375925454],
[-73.8967188588015, 40.851660158514],
[-73.89632720118, 40.8515320489962] ]
The points I want to check are:
1 = [40.8515320489962,-73.89632720118]
2 = [40.8512476593594,-73.8964878416508]
3 = [40.851375925454,-73.8968799791431]
4 = [40.851660158514,-73.8967188588015]
5 = [40.8515320489962,-73.89632720118]
How can I tell if each of these points lies within this polygon?
The algorithm below does not work. I don't know why.
pt[lat,long]
function isPointInPoly(poly, pt){
for(var c = false, i = -1, l = poly.length, j = l - 1; ++i < l; j = i)
((poly[i][1] <= pt[1] && pt[1] < poly[j][1]) || (poly[j][1] <= pt[1] && pt[1] < poly[i][1]))
&& (pt[0] < (poly[j][0] - poly[i][0]) * (pt[1] - poly[i][1]) / (poly[j][1] - poly[i][1]) + poly[i][0])
&& (c = !c);
return c;
}
I don't want to use a third party solution such as google maps API or this one https://github.com/mattwilliamson/Google-Maps-Point-in-Polygon.
My attempt is here:
http://jsfiddle.net/nvNNF/2/
There is a project on Github with code: https://github.com/substack/point-in-polygon (MIT license):
function inside(point, vs) {
// ray-casting algorithm based on
// https://wrf.ecse.rpi.edu/Research/Short_Notes/pnpoly.html/pnpoly.html
var x = point[0], y = point[1];
var inside = false;
for (var i = 0, j = vs.length - 1; i < vs.length; j = i++) {
var xi = vs[i][0], yi = vs[i][1];
var xj = vs[j][0], yj = vs[j][1];
var intersect = ((yi > y) != (yj > y))
&& (x < (xj - xi) * (y - yi) / (yj - yi) + xi);
if (intersect) inside = !inside;
}
return inside;
};
Usage:
// array of coordinates of each vertex of the polygon
var polygon = [ [ 1, 1 ], [ 1, 2 ], [ 2, 2 ], [ 2, 1 ] ];
inside([ 1.5, 1.5 ], polygon); // true
The test function is here: https://github.com/substack/point-in-polygon/blob/master/index.js
Note: This code doesn't work reliably when the point is a corner of the polygon or on an edge. There is an improved version here: https://github.com/mikolalysenko/robust-point-in-polygon
Your polygon array looks like coordinates array in GeoJSON polygon structure (read more at https://macwright.org/2015/03/23/geojson-second-bite.html and http://geojson.org).
So maybe you can use libraries which are working with geoJSON data? Look at answer and comments to OP in Is it possible to determine if a GeoJSON point is inside a GeoJSON polygon using JavasScript?
In short, my day was saved by turf (https://github.com/turfjs/turf)
There is also d3 (https://github.com/d3/d3-geo#geoContains) but i had issues with it.
UPD:
I noticed turf is giving inconsistent results when point is on 'edge' of polygon. I created issue and i am waiting for answer from developers.
UPD2:
'Boundary points' issue is resolved by using latest version of turf (i used 3.0.14 instead of 4.6.1). It's all right now.
Here is the function I finally got working. I got it by adopting C code to javascript from here (with explanation).
function checkcheck (x, y, cornersX, cornersY) {
var i, j=cornersX.length-1 ;
var odd = false;
var pX = cornersX;
var pY = cornersY;
for (i=0; i<cornersX.length; i++) {
if ((pY[i]< y && pY[j]>=y || pY[j]< y && pY[i]>=y)
&& (pX[i]<=x || pX[j]<=x)) {
odd ^= (pX[i] + (y-pY[i])*(pX[j]-pX[i])/(pY[j]-pY[i])) < x;
}
j=i;
}
return odd;
}
Where cornersX = array with x or latitude vertices array, cornersY = array with y or longitude array. X, Y - latitude and longitude of tested point.
In my case i did following thing it's working fine for me
function isLatLngInZone(latLngs,lat,lng){
// latlngs = [{"lat":22.281610498720003,"lng":70.77577162868579},{"lat":22.28065743343672,"lng":70.77624369747241},{"lat":22.280860953131217,"lng":70.77672113067706},{"lat":22.281863655593973,"lng":70.7762061465462}];
vertices_y = new Array();
vertices_x = new Array();
longitude_x = lng;
latitude_y = lat;
latLngs = JSON.parse(latLngs);
var r = 0;
var i = 0;
var j = 0;
var c = 0;
var point = 0;
for(r=0; r<latLngs.length; r++){
vertices_y.push(latLngs[r].lat);
vertices_x.push(latLngs[r].lng);
}
points_polygon = vertices_x.length;
for(i = 0, j = points_polygon; i < points_polygon; j = i++){
point = i;
if(point == points_polygon)
point = 0;
if ( ((vertices_y[point] > latitude_y != (vertices_y[j] > latitude_y)) && (longitude_x < (vertices_x[j] - vertices_x[point]) * (latitude_y - vertices_y[point]) / (vertices_y[j] - vertices_y[point]) + vertices_x[point]) ) )
c = !c;
}
return c;
}
I modernised the function from Aaron's answer:
const getIsPointInsidePolygon = (point: number[], vertices: number[][]) => {
const x = point[0]
const y = point[1]
let inside = false
for (let i = 0, j = vertices.length - 1; i < vertices.length; j = i++) {
const xi = vertices[i][0],
yi = vertices[i][1]
const xj = vertices[j][0],
yj = vertices[j][1]
const intersect = yi > y != yj > y && x < ((xj - xi) * (y - yi)) / (yj - yi) + xi
if (intersect) inside = !inside
}
return inside
}
I want to check if a point lies within a specific polygon. The polygon is:
polygon= [ [-73.89632720118, 40.8515320489962],
[-73.8964878416508, 40.8512476593594],
[-73.8968799791431, 40.851375925454],
[-73.8967188588015, 40.851660158514],
[-73.89632720118, 40.8515320489962] ]
The points I want to check are:
1 = [40.8515320489962,-73.89632720118]
2 = [40.8512476593594,-73.8964878416508]
3 = [40.851375925454,-73.8968799791431]
4 = [40.851660158514,-73.8967188588015]
5 = [40.8515320489962,-73.89632720118]
How can I tell if each of these points lies within this polygon?
The algorithm below does not work. I don't know why.
pt[lat,long]
function isPointInPoly(poly, pt){
for(var c = false, i = -1, l = poly.length, j = l - 1; ++i < l; j = i)
((poly[i][1] <= pt[1] && pt[1] < poly[j][1]) || (poly[j][1] <= pt[1] && pt[1] < poly[i][1]))
&& (pt[0] < (poly[j][0] - poly[i][0]) * (pt[1] - poly[i][1]) / (poly[j][1] - poly[i][1]) + poly[i][0])
&& (c = !c);
return c;
}
I don't want to use a third party solution such as google maps API or this one https://github.com/mattwilliamson/Google-Maps-Point-in-Polygon.
My attempt is here:
http://jsfiddle.net/nvNNF/2/
There is a project on Github with code: https://github.com/substack/point-in-polygon (MIT license):
function inside(point, vs) {
// ray-casting algorithm based on
// https://wrf.ecse.rpi.edu/Research/Short_Notes/pnpoly.html/pnpoly.html
var x = point[0], y = point[1];
var inside = false;
for (var i = 0, j = vs.length - 1; i < vs.length; j = i++) {
var xi = vs[i][0], yi = vs[i][1];
var xj = vs[j][0], yj = vs[j][1];
var intersect = ((yi > y) != (yj > y))
&& (x < (xj - xi) * (y - yi) / (yj - yi) + xi);
if (intersect) inside = !inside;
}
return inside;
};
Usage:
// array of coordinates of each vertex of the polygon
var polygon = [ [ 1, 1 ], [ 1, 2 ], [ 2, 2 ], [ 2, 1 ] ];
inside([ 1.5, 1.5 ], polygon); // true
The test function is here: https://github.com/substack/point-in-polygon/blob/master/index.js
Note: This code doesn't work reliably when the point is a corner of the polygon or on an edge. There is an improved version here: https://github.com/mikolalysenko/robust-point-in-polygon
Your polygon array looks like coordinates array in GeoJSON polygon structure (read more at https://macwright.org/2015/03/23/geojson-second-bite.html and http://geojson.org).
So maybe you can use libraries which are working with geoJSON data? Look at answer and comments to OP in Is it possible to determine if a GeoJSON point is inside a GeoJSON polygon using JavasScript?
In short, my day was saved by turf (https://github.com/turfjs/turf)
There is also d3 (https://github.com/d3/d3-geo#geoContains) but i had issues with it.
UPD:
I noticed turf is giving inconsistent results when point is on 'edge' of polygon. I created issue and i am waiting for answer from developers.
UPD2:
'Boundary points' issue is resolved by using latest version of turf (i used 3.0.14 instead of 4.6.1). It's all right now.
Here is the function I finally got working. I got it by adopting C code to javascript from here (with explanation).
function checkcheck (x, y, cornersX, cornersY) {
var i, j=cornersX.length-1 ;
var odd = false;
var pX = cornersX;
var pY = cornersY;
for (i=0; i<cornersX.length; i++) {
if ((pY[i]< y && pY[j]>=y || pY[j]< y && pY[i]>=y)
&& (pX[i]<=x || pX[j]<=x)) {
odd ^= (pX[i] + (y-pY[i])*(pX[j]-pX[i])/(pY[j]-pY[i])) < x;
}
j=i;
}
return odd;
}
Where cornersX = array with x or latitude vertices array, cornersY = array with y or longitude array. X, Y - latitude and longitude of tested point.
In my case i did following thing it's working fine for me
function isLatLngInZone(latLngs,lat,lng){
// latlngs = [{"lat":22.281610498720003,"lng":70.77577162868579},{"lat":22.28065743343672,"lng":70.77624369747241},{"lat":22.280860953131217,"lng":70.77672113067706},{"lat":22.281863655593973,"lng":70.7762061465462}];
vertices_y = new Array();
vertices_x = new Array();
longitude_x = lng;
latitude_y = lat;
latLngs = JSON.parse(latLngs);
var r = 0;
var i = 0;
var j = 0;
var c = 0;
var point = 0;
for(r=0; r<latLngs.length; r++){
vertices_y.push(latLngs[r].lat);
vertices_x.push(latLngs[r].lng);
}
points_polygon = vertices_x.length;
for(i = 0, j = points_polygon; i < points_polygon; j = i++){
point = i;
if(point == points_polygon)
point = 0;
if ( ((vertices_y[point] > latitude_y != (vertices_y[j] > latitude_y)) && (longitude_x < (vertices_x[j] - vertices_x[point]) * (latitude_y - vertices_y[point]) / (vertices_y[j] - vertices_y[point]) + vertices_x[point]) ) )
c = !c;
}
return c;
}
I modernised the function from Aaron's answer:
const getIsPointInsidePolygon = (point: number[], vertices: number[][]) => {
const x = point[0]
const y = point[1]
let inside = false
for (let i = 0, j = vertices.length - 1; i < vertices.length; j = i++) {
const xi = vertices[i][0],
yi = vertices[i][1]
const xj = vertices[j][0],
yj = vertices[j][1]
const intersect = yi > y != yj > y && x < ((xj - xi) * (y - yi)) / (yj - yi) + xi
if (intersect) inside = !inside
}
return inside
}
I want to add the coordinates x and y (from the loop) to the state (matrix) like you can see in my example but it won't work. Can someone help me?
const [matrix, setMatrix] = useState([[], []] as any)
for (let j = 0; j < imgHeight * scale; j += props.gridsize.height) {
for (let i = 0; i < imgWidth * scale; i += props.gridsize.width) {
console.log('x: ' + x + ' ===== ' + 'y: ' + y)
drawImgRectangles(ctx, [{ x: x, y: y, width: props.gridsize.width, height: props.gridsize.height }])
x += props.gridsize.height
}
x = 0
y += props.gridsize.height
}
setMatrix([...matrix, [[x][y]]])
console.log(matrix[[0][0]]) **
The problem is in expression [x][y] which evaluates to undefined.
[x] defines an array containing one element x
[x][y] tries to index the [x] array, taking y-th element. If y is anything other than 0, the result is undefined
console.log([3][0]); // 3
console.log([3][1]); // undefined
You probably meant one of:
const x = 1;
const y = 2;
var matrix1: number[][] = [];
matrix1 = [...matrix1, [x, y]];
var matrix2: number[][][] = [];
matrix2 = [...matrix2, [[x], [y]]];
I came across the Javascript YarnPattern program from Stanford's CS106AX. However, as I was going through the code, I have difficulty understanding some lines.
In the main function YarnPattern(), I don't quite understand the bold chunk written between the stars " ** ". I'm not quite sure what it means when the variables are initialised with thisPeg = 0 and nextPeg = -1.
Also, I'm not quite sure about the line "nextPeg = (thisPeg + DELTA) % pegs.length". I was wondering how this line of code can help reaching a suitable peg's index position.
It would be great if someone can provide a clear explanation with regards to these lines of code. Your help is much appreciated.
// Constants
const GWINDOW_WIDTH = 1000;
const GWINDOW_HEIGHT = 625;
const N_ACROSS = 80;
const N_DOWN = 50;
const DELTA = 113;
// main function
function YarnPattern() {
let gw = GWindow(GWINDOW_WIDTH, GWINDOW_HEIGHT);
let pegs = createPegArray(GWINDOW_WIDTH, GWINDOW_HEIGHT, N_ACROSS, N_DOWN);
**let thisPeg = 0;
let nextPeg = -1;
while (thisPeg !== 0 || nextPeg === -1) {
nextPeg = (thisPeg + DELTA) % pegs.length;
let p0 = pegs[thisPeg];
let p1 = pegs[nextPeg];
let line = GLine(p0.x, p0.y, p1.x, p1.y);**
line.setColor("Magenta");
gw.add(line);
thisPeg = nextPeg;
}
}
function createPegArray(width, height, nAcross, nDown) {
let dx = width / nAcross;
let dy = height / nDown;
let pegs = [ ];
for (let i = 0; i < nAcross; i++) {
pegs.push(Point(i * dx, 0));
}
for (let i = 0; i < nDown; i++) {
pegs.push(Point(nAcross * dx, i * dy));
}
for (let i = nAcross; i > 0; i--) {
pegs.push(Point(i * dx, nDown * dy));
}
for (let i = nDown; i > 0; i--) {
pegs.push(Point(0, i * dy));
}
return pegs;
}
function Point(x, y) {
if (x === undefined) {
x = 0;
y = 0;
}
return { x: x, y: y };
}
I want to have a flag passed to a function that runs an algorithm by either col-scanning or row-scanning:
if run-on-x
for 1..x
for 1..y
do something with ary[x][y]
else
for 1..y
for 1..x
do something with ary[x][y]
But I don't want to duplicate all the loops and logic.
I've come up with this:
let numPx = width * height;
for (let px = 0; px < numPx; px++) {
let [x, y] = yAxis ? [px % width, 0 | px / width] : [0 | px / height, px % height];
But I think all the math is rather heavy, especially when I'm running it on fairly large arrays.
Is there a better way to do this?
Perhaps by simply passing them in as parameters like so?:
function colRowScan(1stAxis,2ndAxis)
for 1.. 1stAxis
for 1.. 2ndAxis
do something with ary[x][y]
Without seeing what the "do something" is I don't know if there is any unforeseen reasons why this couldn't work but given what you posted it should do the trick.
I am not entirely sure what you are trying to do here:
let numPx = width * height;
for (let px = 0; px < numPx; px++) {
let [x, y] = yAxis ? [px % width, 0 | px / width] : [0 | px / height, px % height];
function f(x, y, on_x) {
var a, b;
if (on_x) {
a = x;
b = y;
}
else {
a = y;
b = x;
}
for (var ia = 0; ia < a.length; ia++) {
for (var ib = 0; ib = b.length; ib++) {
// ...
}
}
}
Keep the two sets of inner and outer loops, but change the body of the inner loop to a single function call. Then there's not much code duplication.
In your solution,
let numPx = width * height;
for (let px = 0; px < numPx; px++) {
let [x, y] = yAxis ? [px % width, 0 | px / width] : [0 | px / height, px % height];
Number of comparison is numPx times while earlier it was only once, leave out the heavy math involved.
I think the simple and best solution is to use a separate function.
OR you can try this
var a, b, fAry;
if (run-on-x) {
a = x;
b = y;
fAry = ary;
} else {
a = y;
b = x;
fAry = transpose of(ary);
}
for (var i = 0; i < a; i++) {
for (var j = 0; j < b; j++) {
do something with fAry[i][j];
}
}
for 1..x
for 1..y {
var a = run-on-x ? ary[x][y] : ary[y][x];
do something with a
}
Create helper functions for row major and column major iteration, taking the array and a function to apply to the array members.
var rowMajor = function (a, op) {
var maxi = a.length;
var maxj = a[0].length;
for(var i = 0; i < maxi; ++i) {
var row = a[i];
for(var j = 0; j < maxj; ++j)
op(row[j],i,j);
}
};
var colMajor = function (a, op) {
var maxi = a.length;
if(maxi === 0) return;
var maxj = a[0].length;
for(var j = 0; j < maxj; ++j) {
for(var i = 0; i < maxi; ++i) {
op(a[i][j],i,j);
}
}
};
// example use (with jQuery)
var array = [[11,12,13],[21,22,23]];
var div = $('<div></div>');
var append = function(value) {
div.append($('<span></span>').text(value + ' '));
};
rowMajor(array,append);
div.append('<br/>');
colMajor(array, append);
$('body').append(div);