【问题标题】:String ArrayList that needs to be converted into a 2 dimensional array需要转换成二维数组的String ArrayList
【发布时间】:2018-12-20 14:29:53
【问题描述】:

背景:

我正在使用 Selenium 进行一个抓取项目,该项目从我们的测试和生产环境中的网页表中获取数据,然后将数据存储到两个单独的字符串类型的数组列表中(一个用于测试/产品)。数据是数字(双),有 3 列和 13-16 行数据。它有所不同,因为我从超过 145 个国家/地区提取数据,并且每个表都不同。

请不要说这只是一个例子。我在这里展示的代码不是我正在运行的 Selenium 脚本。

问题:

问题出在我试图将我拥有的两个数组列表中的数据转换为两个二维数组时。我以前使用过非常基本的二维数组,但只是根据用户输入创建它们。

根据我之前的研究,ArrayList转为数组的语法是:

  ArrayList<String> b = new ArrayList<>();
    b.add("1.50");
    b.add("3.12");
    b.add("5.25%");
    b.add("2.16");
    b.add("4.36");
    b.add("7.76%")
  //This is just a snippet, remember the list would have anywhere from 13-16  
    indices.

  String[] x = b.toArray();

但是如何将相同的列表转换为格式为的二维数组

  1.50 3.12 5.25% 
  2.16 4.36 7.76% 

每隔三个索引开始一个新行?

【问题讨论】:

  • 所以你希望每三个元素都在一个数组中?
  • 是的,上面的2行是一个二维数组。
  • 而不是将您的列表转换为数组(这可能会导致错误,例如,如果页面上缺少某些内容,您最终可能会在一个不属于一起的数组中拥有数据)我建议抓取数据从页面到适当的数据结构,如List&lt;String[]&gt; 或创建一些成本对象。另请查看 Jsoup(HTML parser),了解从网站获取数据的简单方法。
  • @Eritrean Selenium 是最好的工具,因为网页是动态的。此外,这不是项目的结束。到时候,从列表转换为数组将使下一步更容易。

标签: java arrays loops arraylist


【解决方案1】:

您必须循环 List 并将项目添加到新项目中,除非您在其中找到带有百分比 (%) 的值。然后,您创建一个新的List。此解决方案基于% 字符外观,而不是要拆分的元素之间的固定间隙大小,这可能是一个优势。

List<List<String>> outer = new ArrayList<>();
List<String> inner = new ArrayList<>();

for (String s: b) {
    inner.add(s);
    if (s.contains("%")) {
        outer.add(inner);
        inner = new ArrayList<>();
    }
}

List&lt;List&lt;String&gt;&gt; outer 将包含以下值:

[[1.50, 3.12, 5.25%], [2.16, 4.36, 7.76%]]

要将结构从List&lt;List&lt;String&gt;&gt; 转换为String[][],您可以使用 或简单的for 循环方法迭代和填充数组。

String[][] array = outer.stream()
   .map(a -> a.stream().toArray(String[]::new))   // List<String> to String[]
   .toArray(String[][]::new);                     // List<String[]> to String[][]

【讨论】:

    【解决方案2】:

    一个典型的 for 循环应该这样做:

    List<List<String>> accumulator = new ArrayList<>();
    for (int i = 0; i < b.size(); i+=3) {
        List<String> temp = new ArrayList<>(b.subList(i, i + 3));
        accumulator.add(temp);
    }
    

    accumulator 现在看起来像:

    [[1.50, 3.12, 5.25%], [2.16, 4.36, 7.76%]]
    

    请注意,以上假设您将始终是一个三的倍数的列表,如果不是这种情况,那么您可以按如下方式处理它:

    List<List<String>> accumulator = new ArrayList<>();
    for (int i = 0; i < b.size(); i+=3) {
         List<String> temp = b.stream().skip(i).limit(3).collect(toList());
         accumulator.add(temp);
    }
    

    如果你严格要求结果是String[][],那么你可以得到它如下:

     String[][] strings = 
            accumulator.stream()
                       .map(l -> l.toArray(new String[0]))
                       .toArray(String[][]::new);
    

    【讨论】:

    • 这很好,很花哨,但出于特定原因,我需要它在二维数组中,而不仅仅是另一个 ArrayList。
    • @JClark 我也将其作为答案的一部分。
    【解决方案3】:

    您可以遍历列表并在二维数组中手动​​添加条目:

    String[][] array = new String[b.size()/3][3];
    for (int i = 0; i < b.size(); i++) {
      int row = i / 3;
      int col = i % 3;
      array[row][col] = b.get(i);
    }
    
    System.out.println(Arrays.deepToString(array));
    

    【讨论】:

    • 你运行过这段代码吗?我有,我只是以相同的格式打印 arrayList,而不是二维数组。
    • 是的,我测试过了。我将打印数组的代码放在我的答案中。 arrayList 仍然是一个列表。二维数组存储在另一个名为数组的变量中。
    • 你不需要循环,只需调用deepToString即可测试它 --> System.out.println(Arrays.deepToString(array));
    猜你喜欢
    • 2012-06-23
    • 1970-01-01
    • 1970-01-01
    • 2020-09-10
    • 2023-04-03
    • 2021-05-17
    • 2015-06-15
    • 1970-01-01
    • 2013-02-21
    相关资源
    最近更新 更多