Ordering of bidimensional array - javascript

Hello I have the following question:
I have a bidimensional array which look like this:
[[2, C, 22, 22, 8]
[2, C, 22, 22, 7]
[2, C, 22, 22, 10]
[1, R, 45, 45, 4]
[1, R, 45, 45, 3]
[1, R, 45, 45, 2]
[1, R, 45, 45, 1]
[1, R, 150, 100, 6]
[1, R, 150, 100, 5]
[1, C, 22, 22, 9]]
And I want to order the data first for column 1, then for column 2, then for column 3, then for column 4, then for column 5; all in descending order. The following is the result that I want to obtain:
[[2, C, 22, 22, 10]
[2, C, 22, 22, 8]
[2, C, 22, 22, 7]
[1, R, 150, 100, 6]
[1, R, 150, 100, 5]
[1, R, 45, 45, 4]
[1, R, 45, 45, 3]
[1, R, 45, 45, 2]
[1, R, 45, 45, 1]
[1, C, 22, 22, 9]]
I use ExtendScript which is an extended version of Javascript for Adobe.
How is this possible with Javascript?
Any suggestions would be much appreciated.
Thanks in advance

Had the numbers flipped. Updated with working example.
You can use Array.prototype.sort then loop through the options. (make sure to put quotes around your strings though!)
var x = [[2, "C", 22, 22, 8],
[2, "C", 22, 22, 7],
[2, "C", 22, 22, 10],
[1, "R", 45, 45, 4],
[1, "R", 45, 45, 3],
[1, "R", 45, 45, 2],
[1, "R", 45, 45, 1],
[1, "R", 150, 100, 6],
[1, "R", 150, 100, 5] ,
[1, "C", 22, 22, 9]];
x.sort(function(a,b){
for(var i=0; i<a.length; i++) {
if(a[i] > b[i]) {
return -1;
}
if(a[i] < b[i]) {
return 1;
}
}
return 0;
})
Note that I'm assuming that all arrays are the same length and that a simple < and > is sufficient for comparison. If your needs differ it should be trivial to adapt to that.
Working example: http://jsfiddle.net/zSHw9/

Related

How do I rotate a single set of coordinates around an m x n matrix?

I have a single coordinate, say { x: 1, y: 2 } and a matrix size { x: 5, y: 6 }. I would like to rotate that single coordinate around the grid by 90 degrees (clockwise). I can rotate an entire grid by running:
function rotate90(a){
// transpose from http://www.codesuck.com/2012/02/transpose-javascript-array-in-one-line.html
a = Object.keys(a[0]).map(function (c) { return a.map(function (r) { return r[c]; }); });
// row reverse
for (i in a){
a[i] = a[i].reverse();
}
return a;
}
Which takes a grid from:
[1][2][3][4]
[5][6][7][8]
[9][0][1][2]
[3][4][5][6]
to
[3][9][5][1]
[4][0][6][2]
[5][1][7][3]
[6][2][8][4]
How can I do the same with a single coordinate? Some examples on a 4 x 4 grid might be:
0, 0 -> 0, 3
0, 3 -> 3, 3
3, 3 -> 3, 0
3, 0 -> 0, 0
1, 1 -> 1, 2
1, 2 -> 2, 2
2, 2 -> 2, 1
2, 1 -> 1, 1
Starting with a MxN array, (x,y) -> (y,M-x-1)
I used a rotate function inside of a Class when I wrote Tetris.
def rotate(self):
self.rotation = (self.rotation + 1) % len(self.figures[self.type])
I had a list of figures with the rotations in a matrix, the only thing is rather than going to 0 after 9, I continued on with 10.
figures = [
[[8, 9, 10, 11], [2, 6, 10, 14], [11, 10, 9, 8], [13, 9, 5, 1]], #0
[[4, 8, 9, 10], [6, 5, 9, 13], [14, 10, 9, 8], [12, 13, 9, 5]], #1
[[6, 8, 9, 10], [14, 5, 9, 13], [12, 10, 9, 8], [4, 5, 9, 13]], #2
[[5, 6, 10, 9], [5, 6, 10, 9], [5, 6, 10, 9], [5, 6, 10, 9]], #3
[[5, 6, 9, 8], [10, 14, 9, 5], [13, 12, 9, 10], [8, 4, 9, 13]], #4
[[4, 5, 9, 10], [6, 10, 9, 13], [14, 13, 9, 8], [12, 8, 9, 5]], #5
[[5, 8, 9, 10], [5, 10, 9, 13], [13, 10, 9, 8], [8, 13, 9, 5]], #6
]
Since I had multiple figures, I had them selected by random, but you can make it controlled as well
self.type = random.randint(0, len(self.figures) - 1)

Sort by Digit Length, then By Number Itself

How to sort an array of integers by their digit length in descending order, then settles ties by sorting numbers with the same digit length in ascending order.
Examples
digitSort([77, 23, 5, 7, 101])
➞ [101, 23, 77, 5, 7]
digitSort([1, 5, 9, 2, 789, 563, 444])
➞ [444, 563, 789, 1, 2, 5, 9]
digitSort([53219, 3772, 564, 32, 1])
➞ [53219, 3772, 564, 32, 1]
I tried to write my own sort function but it did not help!
Please help
That's the code, if they have same length just return the smaller, otherwise return the longest one.
function digitSort(arr){
return arr.sort((a,b) => {
if(a.toString().length !== b.toString().length) {
return b.toString().length - a.toString().length;
}
return a - b;
})
}
A numerical approach takes the logarithm of 10 as digit count.
const digitSort = array => array.sort((a, b) =>
Math.floor(Math.log10(Math.abs(b))) - Math.floor(Math.log10(Math.abs(a))) ||
a - b
);
console.log(digitSort([77, 23, 5, 7, 101])); // [101, 23, 77, 5, 7]
console.log(digitSort([1, 5, 9, 2, 789, 563, 444])); // [444, 563, 789, 1, 2, 5, 9]
console.log(digitSort([53219, 3772, 564, 32, 1])); // [53219, 3772, 564, 32, 1]
const digitSort = arr => arr.sort((a, b) => String(b).length - String(a).length || a - b)
console.log(digitSort([77, 23, 5, 7, 101])) //[101, 23, 77, 5, 7]
console.log(digitSort([9, 667, 87, 56, 3023, 5555, 111])) //[3023, 5555, 111, 667, 56, 87, 9]
```

Finding all even factorizations of a given number n - javascript python

Currently i am implementing an algorithm that relies on finding all even factorizations of a given number n, including n.
I've tried some things, but overall i am not able to handle the problem well. Maybe its a good idea to handle it recursively, but i am not that good with javascript yet, especially with the higher level aspects of the language which might come in handy.
function evens(n) {
evens = []
for (var i = 2; i < n/2 - 1; i++){
if (i % 2 != 0){
continue;
}
else {
if ((n/i) % 2 == 0) {
evens.push([n/i, i])
}
}
}
return evens
}
This is some code that goes some of the way, but i am not yet able to recursively implement it considering all the right base cases.
I also thought that it could be done with a tree like structure in which paths are even factors, but my cs knowledge is pretty bad.
Suggestions in Python are also welcome, but javascript would be best.
Just to make everything more clear: all even factorizations of 136 for example are [[68, 2], [34, 2, 2], [34, 4], [136]].
Thankfull for any help :)
Maybe its a good idea to handle it recursively
Here's my attempt at a recursive solution in Python:
def even_factorization(n):
solutions = []
def even_divisors(n): # 136 generates [2, 4, 8, 34, 68, 136]
return (d for d in range(2, n + 1, 2) if n % d == 0)
def remove_similarities(array): # [[2, 2, 34], [2, 34, 2], [34, 2, 2]] -> [[2, 2, 34]]
return list(map(list, set(map(lambda a: tuple(sorted(a)), array))))
for divisor in even_divisors(n):
if divisor == n:
solutions.append([divisor])
else:
for solution in even_factorization(n // divisor):
solutions.append([divisor] + solution)
return remove_similarities(solutions) # return 'solutions' to see raw data
For 136 returns:
[[2, 2, 34], [4, 34], [2, 68], [136]]
for 218960 returns:
[[184, 1190], [8, 27370], [4, 54740], [2, 70, 1564], [56, 3910], [2, 2, 170, 322],
[280, 782], [70, 3128], [4, 46, 1190], [2, 2, 34, 1610], [2, 14, 34, 230],
[2, 14, 7820], [20, 34, 322], [10, 14, 34, 46], [14, 92, 170], [20, 46, 238],
[218960], [2, 322, 340], [10, 68, 322], [34, 46, 140], [10, 14, 1564],
[2, 10, 10948], [10, 92, 238], [4, 170, 322], [92, 2380], [14, 20, 782],
[10, 21896], [238, 920], [28, 34, 230], [10, 28, 782], [2, 2, 46, 1190],
[2, 28, 3910], [10, 34, 644], [34, 6440], [2, 92, 1190], [46, 4760], [2, 170, 644],
[2, 68, 1610], [4, 70, 782], [340, 644], [2, 34, 46, 70], [2, 20, 5474],
[14, 68, 230], [2, 34, 3220], [4, 34, 1610], [4, 10, 5474], [28, 7820],
[14, 34, 460], [322, 680], [10, 46, 476], [2, 2, 54740], [4, 230, 238],
[2, 2, 2, 27370], [34, 70, 92], [2, 140, 782], [14, 15640], [2, 10, 46, 238],
[2, 10, 14, 782], [2, 14, 46, 170], [2, 238, 460], [136, 1610], [2, 2, 10, 5474],
[20, 10948], [4, 14, 3910], [40, 5474], [2, 2, 70, 782], [2, 2, 230, 238],
[230, 952], [68, 3220], [2, 46, 2380], [2, 230, 476], [2, 10, 34, 322],
[140, 1564], [460, 476], [170, 1288], [2, 4, 27370], [46, 68, 70], [14, 46, 340],
[2, 109480], [28, 46, 170], [2, 2, 14, 3910]]
After cdlane correctly pointed out a flaw in my solution, I have retracted my original solution, and ported cdlane's elegant python solution to javascript.
function even_factorization(n) {
let solutions = [];
function even_divisors(n) {
var divisors = [];
for (let i = 2; i <= n; i += 2) {
if (n % i === 0) divisors.push(i);
}
return divisors;
}
function remove_similarities(combos) {
for (let i = 0; i < combos.length; i++) {
for (let j = i + 1; j < combos.length; j++) {
if (combos[i].sort((a,b) => a - b).join(" ") === combos[j].sort((a,b) => a - b).join(" ")) {
combos.splice(j--,1);
}
}
}
return combos;
}
even_divisors(n).forEach(divisor => {
if (divisor === n)
solutions.push([divisor]);
else {
even_factorization(n / divisor).forEach(solution => {
solutions.push([divisor, ...solution]);
});
}
});
return remove_similarities(solutions);
}
Running with 218960 returns...
[[2,2,2,27370],[2,2,10,5474],[2,2,14,3910],[2,2,34,1610],[2,2,46,1190],[2,2,70,782],[2,2,170,322],[2,2,230,238],[2,2,54740],[2,4,27370],[2,10,14,782],[2,10,34,322],[2,10,46,238],[2,10,10948],[2,14,34,230],[2,14,46,170],[2,14,7820],[2,20,5474],[2,28,3910],[2,34,46,70],[2,34,3220],[2,46,2380],[2,68,1610],[2,70,1564],[2,92,1190],[2,140,782],[2,170,644],[2,230,476],[2,238,460],[2,322,340],[2,109480],[4,10,5474],[4,14,3910],[4,34,1610],[4,46,1190],[4,70,782],[4,170,322],[4,230,238],[4,54740],[8,27370],[10,14,34,46],[10,14,1564],[10,28,782],[10,34,644],[10,46,476],[10,68,322],[10,92,238],[10,21896],[14,20,782],[14,34,460],[14,46,340],[14,68,230],[14,92,170],[14,15640],[20,34,322],[20,46,238],[20,10948],[28,34,230],[28,46,170],[28,7820],[34,46,140],[34,70,92],[34,6440],[40,5474],[46,68,70],[46,4760],[56,3910],[68,3220],[70,3128],[92,2380],[136,1610],[140,1564],[170,1288],[184,1190],[230,952],[238,920],[280,782],[322,680],[340,644],[460,476],[218960]]
...and running with 136 returns...
[[2,2,34],[2,68],[4,34],[136]]

How to point the range(dataClasses) for 2nd index in data using highcharts?

I have plotted a heatmap using highchart , but i wanted to give color range for y axis ie 2nd index in the data array but it takes 3rd index automatically.
Below is the jsfiddle code.
Links for my code
colorAxis: {
dataClasses: [{
from: 0,
to: 10,
color: 'rgb(191, 27, 0)'
},{
from:10,
to:30,
color:'rgb(234, 100, 96)'
},{
from:30,
to:100,
color:'rgb(242, 201, 109)'
},{
from:100,
color:'rgb(98, 158, 81)'
}]
},
series: [{
name: 'Sales per employee',
borderWidth: 1,
data: [[0, 0, 10], [0, 1, 19], [0, 2, 8], [0, 3, 24], [0, 4, 67], [1, 0, 92], [1, 1, 58], [1, 2, 78], [1, 3, 117], [1, 4, 48], [2, 0, 35], [2, 1, 15], [2, 2, 123], [2, 3, 64], [2, 4, 52], [3, 0, 72], [3, 1, 132], [3, 2, 114], [3, 3, 19], [3, 4, 16], [4, 0, 38], [4, 1, 5], [4, 2, 8], [4, 3, 117], [4, 4, 115], [5, 0, 88], [5, 1, 32], [5, 2, 12], [5, 3, 6], [5, 4, 120], [6, 0, 13], [6, 1, 44], [6, 2, 88], [6, 3, 98], [6, 4, 96], [7, 0, 31], [7, 1, 1], [7, 2, 82], [7, 3, 32], [7, 4, 30], [8, 0, 85], [8, 1, 97], [8, 2, 123], [8, 3, 64], [8, 4, 84], [9, 0, 47], [9, 1, 99], [9, 2, 31], [9, 3, 48], [9, 4, 91]],
dataLabels: {
enabled: true,
color: '#000000'
}
}]
The actual data is in below format
data: [[0, 0, 10], [0, 1, 19]]
Now range is plotted on the base of 2nd index ie 10,19 but i want to plot based on 1st index ie 0,1.
Change the default name of the property (of point object) that'll be used to compute the color :
Highcharts.seriesTypes.heatmap.prototype.colorKey = 'x'; // 'value' by default
Live demo: http://jsfiddle.net/BlackLabel/z3b1Lcqg/
Docs: https://www.highcharts.com/docs/extending-highcharts/extending-highcharts

How do I make a list of all possible sums from 2 arrays?

For example let's say I have arrays
a = [1, 2, 3, 4, 5, 6] and b = a
And the output I expect would be:
1 + 1, 1 + 2, 1 + 3 ... 3 + 1, 3 + 2, 3 + 4 ... 6 + 3, 6 + 4, 6 + 5, 6 + 6
I would prefer to make this simple calculation in JS or Ruby, but I don't mind answer in any other language. Can anyone provide me any direction?
In Ruby:
a.product(b).map {|p| p.reduce(:+) }.uniq
a = [1, 2, 3, 4, 5, 6]
b = [1, 4, -1, 7, 9]
a.product(b).map { |a,b| a+b }.uniq
#=> [2, 5, 0, 8, 10, 3, 6, 1, 9, 11, 4, 7, 12, 13, 14, 15]
The steps:
c = a.product(b)
#=> [[1, 1], [1, 4], [1, -1], [1, 7], [1, 9],
# [2, 1], [2, 4], [2, -1], [2, 7], [2, 9],
# [3, 1], [3, 4], [3, -1], [3, 7], [3, 9],
# [4, 1], [4, 4], [4, -1], [4, 7], [4, 9],
# [5, 1], [5, 4], [5, -1], [5, 7], [5, 9],
# [6, 1], [6, 4], [6, -1], [6, 7], [6, 9]]
d = c.map { |a,b| a+b }
#=> [2, 5, 0, 8, 10,
# 3, 6, 1, 9, 11,
# 4, 7, 2, 10, 12,
# 5, 8, 3, 11, 13,
# 6, 9, 4, 12, 14,
# 7, 10, 5, 13, 15]
d.uniq
#=> [2, 5, 0, 8, 10, 3, 6, 1, 9, 11, 4, 7, 12, 13, 14, 15]
In javascript, get unique sums using Set
var a = [1, 2, 3, 4, 5, 6];
var r = new Set();
a.forEach(x => a.forEach(y => r.add(x + y)))
document.write('<pre>' + Array.from(r) + '</pre>');
You can use Array.prototype.forEach() for the iteration over the arrays.
The forEach() method executes a provided function once per array element.
The result is without repeat.
function xSums(array) {
var r = [],
o = {};
array.forEach(function (a) {
array.forEach(function (b) {
if (!o[a + b]) {
r.push(b + a);
o[a + b] = true;
}
});
});
return r;
}
document.write('<pre>' + JSON.stringify(xSums([1, 2, 3, 4, 5]), 0, 4) + '</pre>');
document.write('<pre>' + JSON.stringify(xSums([3, 7, 42]), 0, 4) + '</pre>');
I would do something like this:
a = [1, 2, 3, 4, 5, 6]
a.permutation(2).map { |x, y| x + y }
Try looping through both arrays, adding the first to the second, and storing the results in a third, eg;
var one = [1, 2, 3];
var two = [4, 5, 6];
var three = [];
for(var x = 0; x < one.length; ×++){
for(var y = 0; y < two.length; y++){
three.push(one[x] + two[y]);
}
}
This would result in three[0] = 1 + 4, three[1] = 1+ 5, three[2] =1+ 6, three[3] = 2 + 4, three[4] = 2+ 5 etc...

Categories