【问题标题】:find Math.min row找到 Math.min 行
【发布时间】:2020-05-13 02:42:28
【问题描述】:

我已经在 csv 文件的列中找到了最小值,但我找不到存储该值的行。有人能帮助我吗?无论如何我可以自己找到答案,尽管我已经搜索了很多天和网站。提前致谢。

function getDataPointsFromCSV(csv) {
            var dataPoints = csvLines =   [];   
            var mini, a
            var minIndex = 0
            csvLines = csv.split(/[\r?\n|\r|\n]+/);
            for (var i = 1; i <= csvLines.length; i++)
                if (csvLines[i] > 0) {
                    points = csvLines[i].split(",");
//points instead of csvLines
                    mini = points[4]
                }
            var a = mini                
            for (var i = 1; i <= csvLines.length; i++)
                if (csvLines[i] < mini) {
                    points = csvLines[i].split(",");                    

                    minIndex = i
                    mini = csvLines[i]                                      
// Find lowest value in a column5(=points[4])( but how to find the row that store the lowest value, can someone help me please?)                
                    lowestv = Math.min(price, lowestv)
             }
// example; mini.length          
            for (var i = mini.length; i <= mini.length+10; i++)
                if (csvLines[i].length > 0) {
                    points = csvLines[i].split(",");
                    price = points[4]
            }
                dataPoints.push({x: new Date(),y: parseFloat(minIndex)});   
        return dataPoints;
        }

【问题讨论】:

  • 稍加修改后是否可以将这些代码插入到我的程序中?var col2 = arr.map(function (elem) { return elem[1]; //to get all the column 2 values }); var index = col2.indexOf(Math.max.apply(this, col2));
  • 只是为了好玩:您能否添加您使用的 CSV 样本(如标题 + 3 或 4 行)?
  • **日期开高低靠近31/10/2019 9202.457589 9383.160892 9199.584833 9028.71744 30/10/2019 9422.463325 9426.874217 9085.370357 9205.726559 9248.440562 29/10/2019 9516.181048 9232.648086 9427.687584 9565.101883 28/10/2019 9805.118089 9256.148389 9256.148389 **

标签: javascript csv row min


【解决方案1】:

我会将其分为两个步骤。首先,我们解析 CSV 以获取对象数组。然后我们遍历它们以找到像 minValminRow 之类的统计数据(以及我们可能想要的任何其他数据。)虽然这比一次执行效率略低,但它会导致更简单、更易于维护的代码。

所以这里有csv2arr,它将您的 CSV 字符串转换为如下所示的对象:

{
    date: "31/10/2019",
    open: 9202.457589,
    high: 9383.160892,
    low: 9028.71744,
    close: 9199.584833
}

stats,它采用类似的对象数组来查找每列的统计信息,例如maxValminRow。如果需要,我们可以增强它以查找其他统计信息,例如 meanmedian。它的输出如下所示:

{
    date: { /* ... */ },
    open: { /* ... */ },
    high: { /* ... */ },
    low: { /* ... */ },
    close: {
        minVal: 9199.584833,
        maxVal: 9427.687584,
        minRow: {date: "31/10/2019", open: 9202.457589, high: 9383.160892, low: 9028.71744, close: 9199.584833},
        maxRow: {date: "29/10/2019", open: 9248.440562, high: 9516.181048, low: 9232.648086, close: 9427.687584}
    }
}

这是一种方法:

// Naive, but useful for some data
const csv2arr = (csv) => {
  const [headers, ...rows] = csv .trim () .split ('\n') .map (r => r .split (','))
  return rows .reduce ((a, r) => [
    ... a, 
    Object .assign (... (r .map ((c, i) => ({[headers [i]]: isNaN(c) ? c : Number(c)}))))
  ], [])
}

const stats = (rows) => rows .reduce (
  (stats, row) => Object .assign (
    ... Object .entries (row) .map (([key, val]) => ({[key]: ({
      minVal: key in stats && stats [key] .minVal < val ? stats [key] .minVal : val,
      maxVal: key in stats && stats [key] .maxVal > val ? stats [key] .maxVal : val,
      minRow: key in stats && stats [key] .minRow [key] < val ? stats [key] .minRow : row,
      maxRow: key in stats && stats [key] .maxRow [key] > val ? stats [key] .maxRow : row,
    })}))
  ),
  {}
)

const csv = `
date,open,high,low,close
31/10/2019,9202.457589,9383.160892,9028.71744,9199.584833
30/10/2019,9422.463325,9426.874217,9085.370357,9205.726559
29/10/2019,9248.440562,9516.181048,9232.648086,9427.687584
28/10/2019,9565.101883,9805.118089,9256.148389,9256.148389
`

const rows = csv2arr (csv)
const statistics = stats (rows)

console .log (rows)
console .log (statistics)

请注意,此处日期的最小值/最大值没有多大意义。如果它们是 ISO 格式的(例如“2019-10-31”),那么这些值也会得到有意义的最大值和最小值。

csv2arr 适用于相当广泛的情况。但不要将其误认为是完整的 CSV 解析器。例如,如果您的数据包含带逗号的单元格,它将失败。它对输出也很幼稚。本质上,如果它看起来像一个数字,它就会变成一个数字,即使列中的其他内容不同意。还有其他问题。但它仍然适用于许多逗号分隔格式。

【讨论】:

  • @Steve:我认为这是你的决定。我的回答提供了两个功能。将带有标题的 CSV 字符串转换为具有由这些标题命名的属性的对象数组。另一个查找此类对象数组的最小/最大值和行。我没有仔细查看您的代码,但我希望这种组合将是它的 替换,而不是它调用的东西。
  • 我认为这些函数不适合我,因为我想做的是找到lowestv.length并将其放入循环for (var i = lowestv.length; i &lt;= lowestv.length+10; i++)var i从存储最低值的行开始var i = 1
  • @Steve:我的函数很可能对你一点帮助都没有。但他们试图以一般方式解决您的问题。因此,例如,如果最后您检查了statistics .close .minRow,您将得到一个类似于:{date: "31/10/2019", open: 9202.457589, high: 9383.160892, low: 9028.71744, close: 9199.584833} 的值。如果这不是您想要的那种输出,那么这可能不适合您。
【解决方案2】:

我提供了一个 sn-p,它使用了您评论中的示例数据:

const csv = "date,open,high,low,close\n31/10/2019,9202.457589,9383.160892,9028.71744,9199.584833\n30/10/2019,9422.463325,9426.874217,9085.370357,9205.726559\n29/10/2019,9248.440562,9516.181048,9232.648086,9427.687584\n28/10/2019,9565.101883,9805.118089,9256.148389,9256.148389"
const lines = csv.split(/[\r?\n|\r|\n]+/)
const header = lines.shift().split(',') // chop off header, and store it in a variable
const cells = lines.map(e => e.split(',').map(n => !isNaN(n) ? Number(n) : n))

// transpose the array, so it's easier to get min/max
// transposing (rows become columns and columns become rows)
// [[a, b],[c, d]] ==> [[a, c], [b, d]]
const transpose = cells[0].map((e, i) => {
  return cells.map(el => {
    return el[i]
  })
})
const dates = transpose.shift() // chop off dates, and store them in a variable

const rowRange = transpose.map((e, i) => {
  const min = Math.min(...e)
  const max = Math.max(...e)
  return {
    col: i + 1, // +1, because dates are chopped off
    colName: header[i + 1],
    max,
    maxRow: e.indexOf(max) + 1, // +1, because header is chopped off
    maxRowDate: dates[e.indexOf(max)],
    min,
    minRow: e.indexOf(min) + 1, // +1, because header is chopped off
    minRowDate: dates[e.indexOf(min)]
  }
})

console.log("result:", rowRange)

我添加了 min AND ma​​x(以及其他几个属性),以便您可以在更多情况下使用它。

重要提示

此解决方案会改变从 CSV 解析的数组。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-02-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-31
    • 2023-04-05
    • 1970-01-01
    相关资源
    最近更新 更多