使用 Javascript 的嵌套数组循环在所有象限中生成和排序 (0,0) 附近的笛卡尔坐标

Posted

技术标签:

【中文标题】使用 Javascript 的嵌套数组循环在所有象限中生成和排序 (0,0) 附近的笛卡尔坐标【英文标题】:Generate and sort cartesian coordinates around (0,0) in all quadrants using Javascript's nested array loops 【发布时间】:2021-12-15 04:17:57 【问题描述】:

我有一个变量obj,它的元素计数需要笛卡尔坐标。

所以我想生成如下矩阵。

obj = 9,obj 的平方根 = 3,3x3 矩阵
(-1,1) (0,1) (1,1)
(-1,0) (0,0) (1,0)
(-1,-1) (0,-1) (1,-1)
obj = 25,obj 的平方根 = 5,5x5 矩阵
(-2,2) (-1,2) (0,2) (1,2) (2,2)
(-2,1) (-1,1) (0,1) (1,1) (2,1)
(-2,0) (-1,0) (0,0) (1,0) (2,0)
(-2,-1) (-1,-1) (0,-1) (1,-1) (2,-1)
(-2,-2) (-1,-2) (0,-2) (1,-2) (2,-2)
obj = 49,obj 的平方根 = 7,7x7 矩阵
(-3,3) (-2,3) (-1,3) (0,3) (1,3) (2,3) (3,3)
(-3,2) (-2,2) (-1,2) (0,2) (1,2) (2,2) (3,2)
(-3,1) (-2,1) (-1,1) (0,1) (1,1) (2,1) (3,1)
(-3,0) (-2,0) (-1,0) (0,0) (1,0) (2,0) (3,0)
(-3,-1) (-2,-1) (-1,-1) (0,-1) (1,-1) (2,-1) (3,-1)
(-3,-2) (-2,-2) (-1,-2) (0,-2) (1,-2) (2,-2) (3,-2)
(-3,-3) (-2,-3) (-1,-3) (0,-3) (1,-3) (2,-3) (3,-3)

我所做的是硬编码第一组,即当 obj 值为 9 时在循环内创建,并将它们推送到名为 coordinates 的列表中。

然后我所做的就是通过传递 Math.sqrt(obj) 来调用循环。

问题:

obj 值大于9 时,存在缺少坐标。 例如:obj 值为 49 时。它会创建相邻的前一个元素,但不会创建前一个元素的前一个元素(坐标如 (-1, 3), (1, 3), ( -3, 1), (3, 1), (-3, -1), (3, -1), (-1, -3), (1, -3))。 发生这种情况是因为我硬编码了逻辑以通过减去 1 创建前一个坐标。随着obj 值的增加,当前缺失坐标的数量是之前缺失元素数量的两倍(不确定)。 我似乎无法找到一种方法来创建创建缺失元素的逻辑。 另一个问题是重复坐标。发生这种情况是因为我使用了错误的逻辑来创建缺失的元素。 当计数 (obj) 值增加时,很难检查所有坐标是否正确

注意:

我想知道在 (0, 0) 周围创建笛卡尔坐标的不同方法。显然,我在构建逻辑方面所做的所有努力都以缺少元素或重复元素而告终。当obj 值增加时,很难真正检查所有坐标是否正确。

我想创建一个任意值的笛卡尔坐标矩阵。目前我坚持使用奇数的平方(当数字小于或大于奇数的平方时,我计划用 0 轴代替)。

方法想法/概念进行测试:

由于我是图形编程的初学者,我想知道更好的方法来做到这一点。这里还有一些我刚刚想出的方法。我不确定这是否有效,但我会添加更新。

    我也许可以只为 0 的 (x,y) axis 创建一个交叉。然后尝试通过对axis 中的每个坐标进行减法或加法来创建其余元素。

    由于有 4 个象限,我可以创建 4 个单独的循环来创建该特定象限的缺失坐标。

    (0,1)
    (-1,0) (0,0) (1,0)
    (0,-1)

    另一种方法是对坐标进行排序,然后检查两个相邻坐标之间的距离,如果大于 1,则创建一个新元素,否则继续检查。

当前代码:

My demo code at JSFiddle

const speak = 'these are the COORDINATES you are looking for!'
// 9, 25, 49, 81, 121 => substitutable values for variable 'obj'
const obj = 49 // loop using this variable
const coordinates = []

// hardcodes
const start = [0,0]
const points = []
/* points.push(start) */


/**
 * FIX!.
 *
 * needs to also create coordinates from initial coordinate substracted
 * by more than 1, currently it gets the previous element by substracting 1,
 * we need to get previous elements of the previous elements based on number
 * of elements.
 */

// creating array from coordinates in all quadrants
function demo (n) 
    // pushing initial coordinates
    for (let i = 1; i <= Math.sqrt(n); i++) 
    
    coordinates.push([-i, i], [i-1, i], [i, i], [-i, i-1], [i-1, i-1], [i, i-1], [-i, -i], [i-1, -i],  [i, -i])
    for (let j = 3; j < Math.sqrt(n); j++) 
        coordinates.push([-i, i-j], [i-j, i-j], [i, i-j], [i-j, -i])
    
  
  // pushing missing coordinates
/*   for (let i = 1; i <= Math.sqrt(n); i++) 
    coordinates.push([i-2, i], [-i, i-2], [i-2, i-2], [i, i-2])
   */

for (let i = 0; i < obj; i++) 
      points.push(coordinates[i])
  


demo(obj)
// sorting multidimensional array
points.sort(function (a, b) 
  return a[1] - b[1]
)

/* // print array as row and column of coordinates
for (let x = 0; x < Math.sqrt(obj); x++) 
  let el = []
  for (let i = 0; i < Math.sqrt(obj); i++)
    el.push(points[i + Math.sqrt(obj) * x])
  
  console.log(el)
*/

【问题讨论】:

请为 4x4 表格添加结果。 【参考方案1】:

如果我理解正确,您希望坐标按顺序排列,左上角在前,右下角在后,对吧?

你可以这样试试

let
  size = 81, //ie a 7x7 grid,
  rc = Math.floor(Math.sqrt(size))  //number of rows/columns
  max = Math.floor(rc / 2),  //maximum x and y coordinates
  min = -1 * max;  //minimim x and y coordinates
  coords = [] //the array of coordinates
  
//as the positive y coordinates should be first, iterate from max down to min
for (let y = max; y >= min; y--) 
  //for each row, iterate the x cooridinates from min up to max
  for (let x = min; x <= max; x++)
    coords.push([x,y]);
    
    
    
for (let i = 0; i < rc; i++) 
  let row = coords.slice(i*rc, (i+1)*rc);  //get one full row of coordinates
  console.log(row.map(x => formatCoordinate(x)).join(""));  //and display it



function formatCoordinate(x) 
  return "|" + `$x[0]`.padStart(3, " ") + "/" + `$x[1]`.padStart(3, " ") + "|"  

另一种方法是,只需将坐标以任意顺序放入数组中,然后对值进行排序。但是你必须按照xy坐标排序,

let
  size = 81, //ie a 7x7 grid,
  rc = Math.floor(Math.sqrt(size))  //number of rows/columns
  max = Math.floor(rc / 2),  //maximum x and y coordinates
  min = -1 * max;  //minimim x and y coordinates
  coords = [] //the array of coordinates

//coords will be [[-3, -3], [-3, -2], [-3, -1] ..., [3, 3]]
for (let i = min; i <= max; i++)
  for (let j = min; j <= max; j++)
    coords.push([i,j]);
    


//sort coords to be [[-3, 3], [-2, 3], [-1, 3], ... [3, -3]]
coords.sort((a, b) => 
  if (a[1] != b[1])  //if y coordinates are different
    return b[1] - a[1];  //higher y coordinates come first
   
  return a[0] - b[0];  //lower x coordinates come firs
)

for (let i = 0; i < rc; i++) 
  let row = coords.slice(i*rc, (i+1)*rc);  //get one full row of coordinates
  console.log(row.map(x => formatCoordinate(x)).join(""));  //and display it


function formatCoordinate(x) 
  return "|" + `$x[0]`.padStart(3, " ") + "/" + `$x[1]`.padStart(3, " ") + "|"  

这两种方法都假定size 是奇数的平方,但您当然可以根据需要调整它们,即原则上您只需将minmax 设置为您想要的任何值, 两种方法都会从[[min/max] ... [max/min]] 创建一个坐标平方。

【讨论】:

以上是关于使用 Javascript 的嵌套数组循环在所有象限中生成和排序 (0,0) 附近的笛卡尔坐标的主要内容,如果未能解决你的问题,请参考以下文章

json #AngularJS,#JavaScript:使用ng-repeat循环遍历嵌套数组

带有嵌套循环的多维数组Javascript

javascript 数组对象与嵌套循环写法

Javascript怎么跳出循环,嵌套循环。

带有嵌套for循环的Javascript多维数组-无法正常工作

Node.js 循环遍历嵌套的 Javascript 对象