Javascript 修剪并添加到二维阵列以形成矩形
我有一个2d数组,Javascript 修剪并添加到二维阵列以形成矩形,javascript,arrays,multidimensional-array,Javascript,Arrays,Multidimensional Array,我有一个2d数组,块。这个数组有很多空格,因为它是用户生成的,所以我不能手动填充它。它可能看起来像这样: let blocks = [ [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0], [0,0,0,0,0,0,0,0,1,0,0,0,0,0,0], [0,0,0,1,0,1,0,0,1,0,0,0,0,0,0], [0,1,1,1,1,3,1,1,1,1,1,0,0,0,0], [0,1,1,2,2,1,1,1,1,2,1,1,0,0,0], [0,1,
块
。这个数组有很多空格,因为它是用户生成的,所以我不能手动填充它。它可能看起来像这样:
let blocks = [
[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
[0,0,0,0,0,0,0,0,1,0,0,0,0,0,0],
[0,0,0,1,0,1,0,0,1,0,0,0,0,0,0],
[0,1,1,1,1,3,1,1,1,1,1,0,0,0,0],
[0,1,1,2,2,1,1,1,1,2,1,1,0,0,0],
[0,1,1,1,1,2,1,3,1,1,1,1,3,0,0],
[0,0,0,0,0,1,1,1,2,0,1,0,1,0,0],
[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0]
];
它没有完全的直边,也不一定居中。我需要把它转换成一个完整的recanglular网格,没有任何空格。现在,一个简单的方法是只取所有的0,并将其转换为填充颜色,如1。这会起作用,但会为网格创建非常大的地图,而网格可能要小得多。因为边不是直的,所以我仍然需要使用填充物,但我希望使用尽可能少的填充物,并为任何网格创建尽可能小的贴图
在上述情况下,这将是解决方案:
let blocks = [
[1,1,1,1,1,1,1,1,1,1,1,1],
[1,1,1,1,1,1,1,1,1,1,1,1],
[1,1,1,1,3,1,1,1,1,1,1,1],
[1,1,2,2,1,1,1,1,2,1,1,1],
[1,1,1,1,2,1,3,1,1,1,1,3],
[1,1,1,1,1,1,1,2,1,1,1,1],
];
在js中我该如何做
下面是代码,请注意末端数组是1d,不同的东西映射到不同的数字,但基本原理仍然相同:
//Clip untill rectangle
let minX = 0;
let minY = 0;
let maxX = 0;
let maxY = 0;
for(let y in this.map){
for(let x in this.map[y]){
if(this.map[y][x] != 'blank'){
maxY = Math.max(y, maxY);
minY = Math.min(y, minY);
maxX = Math.max(x, maxX);
minX = Math.min(x, minX);
}
}
}
console.log(minX, minY, maxX, maxY)
//we now know the width and height
let w = maxX - minX;
let h = maxY - minY;
//fill it up
for(let y = minY; y < maxY; y++){
for(let x = minX; x<= maxX; x++){
let X = x - minX;
let Y = y - minY;
let place;//what we will place
switch(this.map[y][x]){
case 'blank':
place = 1 + fillTheme;
break;
case 'open':
place = 0;
break;
case 'player up':
place = 5;
break;
case 'player left':
place = 6;
break;
case 'player down':
place = 7;
break;
case 'player right':
place = 8;
break;
}
map[Y*w+X] = place;
}
}
//剪切到矩形
设minX=0;
设minY=0;
设maxX=0;
设maxY=0;
for(让y在这个.map中){
for(让x在这个.map[y]中){
if(this.map[y][x]!='blank'){
maxY=Math.max(y,maxY);
minY=Math.min(y,minY);
maxX=Math.max(x,maxX);
minX=Math.min(x,minX);
}
}
}
log(minX,minY,maxX,maxY)
//我们现在知道了宽度和高度
设w=maxX-minX;
设h=maxY-minY;
//加满
for(设y=minY;y 对于(让x=minX;x可以迭代数组,过滤空行并收集列信息,这些信息用于对过滤后的行进行切片,然后将falsy值映射为一个
“0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,[0,0,0,0,0,0,1,1,2,0,1,0,0,0,0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]],
cols=[],
行=块。过滤器(a=>{
设row=false;
a、 forEach((v,i)=>{
cols[i]=cols[i]| | v;
行=行| | v;
});
返回行;
}),
指数=cols.reduce((r,v,i)=>{
如果(v)返回[r[0],i+1];
如果(r[0]==i)r[0]++;
返回r;
}, [0, 0]),
result=rows.map(a=>a.slice(…索引).map(v=>v | | 1));
控制台日志(索引);
result.forEach(a=>console.log(…a));
.as console wrapper{max height:100%!important;top:0;}
您可以迭代数组并过滤空行并收集列信息,这些信息用于对过滤的行进行切片,然后将falsy值映射为一个
“0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,[0,0,0,0,0,0,1,1,2,0,1,0,0,0,0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]],
cols=[],
行=块。过滤器(a=>{
设row=false;
a、 forEach((v,i)=>{
cols[i]=cols[i]| | v;
行=行| | v;
});
返回行;
}),
指数=cols.reduce((r,v,i)=>{
如果(v)返回[r[0],i+1];
如果(r[0]==i)r[0]++;
返回r;
}, [0, 0]),
result=rows.map(a=>a.slice(…索引).map(v=>v | | 1));
控制台日志(索引);
result.forEach(a=>console.log(…a));
。作为控制台包装{最大高度:100%!重要;顶部:0;}
遍历所有行和列一次,标记要删除的行和列。
现在,使用filter
和map
使用上述行
和cols
可以轻松获得所需的输出
let块=[
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0],
[0, 1, 1, 1, 1, 3, 1, 1, 1, 1, 1, 0, 0, 0, 0],
[0, 1, 1, 2, 2, 1, 1, 1, 1, 2, 1, 1, 0, 0, 0],
[0, 1, 1, 1, 1, 2, 1, 3, 1, 1, 1, 1, 3, 0, 0],
[0, 0, 0, 0, 0, 1, 1, 1, 2, 0, 1, 0, 1, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
];
const rows=blocks.map(()=>true);
常量cols=块[0]。映射(()=>true);
for(设i=0;i!行[i])
.map((arr)=>arr.filter((uj)=>!cols[j]).map((x)=>(x==0?1:x));
res.forEach((行)=>console.log(JSON.stringify(行));
遍历一次所有行和列,标记要删除的行和列。
现在,使用filter
和map
使用上述行
和cols
可以轻松获得所需的输出
let块=[
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0],
[0, 1, 1, 1, 1, 3, 1, 1, 1, 1, 1, 0, 0, 0, 0],
[0, 1, 1, 2, 2, 1, 1, 1, 1, 2, 1, 1, 0, 0, 0],
[0, 1, 1, 1, 1, 2, 1, 3, 1, 1, 1, 1, 3, 0, 0],
[0, 0, 0, 0, 0, 1, 1, 1, 2, 0, 1, 0, 1, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
];
const rows=blocks.map(()=>true);
常量cols=块[0]。映射(()=>true);
for(设i=0;i