重复一个数组元素

编程入门 行业动态 更新时间:2024-10-20 09:30:05
本文介绍了重复一个数组元素的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧! 问题描述

我怎么能重复一个数组的元素在Java中?

How can I repeat the elements of an array in Java?

,例如,给定阵列 {A,B,C,D,E,F} 等一批 N ,我想产生一个 N -element阵列看起来像 {A,b,C,D,E,F,A,b ,C,D,E,F,A,b,C,...} 。

For example, given the array {a,b,c,d,e,f} and a number n, I want to produce an n-element array that looks like {a,b,c,d,e,f,a,b,c,d,e,f,a,b,c,...}.

如果我知道事先输入和输出数组的长度,我可以这样写:

If I knew the length of the input and output arrays in advance, I could just write something like this:

int a=input[0], b=input[1], c=input[2], d=input[3], e=input[4], f=input[5]; int[] array = new int[n]; array[0]=a; array[1]=b; array[2]=c; array[3]=d; array[4]=e; array[5]=f; array[6]=a; array[7]=b; array[8]=c; array[9]=d; array[10]=e; array[11]=f; array[12]=a; array[13]=b; array[14]=c; // .. and so on

但我怎么能做到这一点,如果我不知道的长度吗?我想我将不得不使用某种形式的循环,但我不知道怎么写的。还是有重复Java中的数组一些内置的方式,像其他一些语言有?

But how can I do this if I don't know the lengths yet? I assume I would have to use a loop of some kind, but I'm not sure how to write one. Or is there some built-in way to repeat an array in Java, like some other languages have?

推荐答案

这实现比这里显示的其他更清洁,更快速。

This implementation is much cleaner and faster than the others shown here.

public static <T> T[] repeat(T[] arr, int newLength) { T[] dup = Arrays.copyOf(arr, newLength); for (int last = arr.length; last != 0 && last < newLength; last <<= 1) { System.arraycopy(dup, 0, dup, last, Math.min(last << 1, newLength) - last); } return dup; }

System.arraycopy 是本机调用。因此,这是非常快的,但它并不意味着它是最快的方法。

Theory

System.arraycopy is a native call. Therefore it is very fast but it doesn't mean it is the fastest way.

每一个其他的解决办法copys通过元素的数组元素。我的解决方案copys更大的块。每次迭代复制数组中的现有元素,这意味着循环将最多运行的 LOG2(N)倍。

Every other solution copys the array element by element. My solution copys larger blocks. Every iteration duplicates the existing elements in the array which means the loop will run at most log2(n) times.

下面是我的标杆code重现的结果:

Here is my benchmark code to reproduce the results:

import org.openjdk.jmh.annotations.Benchmark; import org.openjdk.jmh.annotations.BenchmarkMode; import org.openjdk.jmh.annotations.Fork; import org.openjdk.jmh.annotations.Measurement; import org.openjdk.jmh.annotations.Mode; import org.openjdk.jmh.annotations.OutputTimeUnit; import org.openjdk.jmh.annotations.Scope; import org.openjdk.jmh.annotations.State; import org.openjdk.jmh.annotations.Threads; import org.openjdk.jmh.annotations.Warmup; @Fork(3) @BenchmarkMode(Mode.AverageTime) @Measurement(iterations = 10, timeUnit = TimeUnit.NANOSECONDS) @State(Scope.Benchmark) @Threads(1) @Warmup(iterations = 5, timeUnit = TimeUnit.NANOSECONDS) @OutputTimeUnit(TimeUnit.NANOSECONDS) public class MyBenchmark { private static final String[] TEST_ARRAY = { "a", "b", "c", "d", "e", "f" }; private static final int NEW_LENGTH = 10_000; @Benchmark public String[] testMethod() { String[] dup = Arrays.copyOf(TEST_ARRAY, NEW_LENGTH); for (int last = TEST_ARRAY.length; last != 0 && last < NEW_LENGTH; last <<= 1) { System.arraycopy(dup, 0, dup, last, Math.min(last << 1, NEW_LENGTH) - last); } return dup; } @Benchmark public String[] testMethod1() { String[] arr = new String[NEW_LENGTH]; for (int i = 0; i < NEW_LENGTH; i++) { arr[i] = TEST_ARRAY[i % TEST_ARRAY.length]; } return arr; } @Benchmark public String[] testMethod2() { List<String> initialLetters = Arrays.asList(TEST_ARRAY); List<String> results = new ArrayList<>(); int indexOfLetterToAdd = 0; for (int i = 0; i < 10000; i++) { results.add(initialLetters.get(indexOfLetterToAdd++)); if (indexOfLetterToAdd == initialLetters.size()) { indexOfLetterToAdd = 0; } } return results.toArray(new String[results.size()]); } @Benchmark public String[] testMethod3() { String result[] = new String[NEW_LENGTH]; for (int i = 0, j = 0; i < NEW_LENGTH && j < TEST_ARRAY.length; i++, j++) { result[i] = TEST_ARRAY[j]; if (j == TEST_ARRAY.length - 1) { j = -1; } } return result; } @Benchmark public String[] testMethod4() { String[] result = Stream.iterate(TEST_ARRAY, x -> x).flatMap(x -> Stream.of(TEST_ARRAY)).limit(NEW_LENGTH) .toArray(String[]::new); return result; } }

结果

Benchmark Mode Cnt Score Error Units MyBenchmark.testMethod avgt 30 4154,553 ± 11,242 ns/op MyBenchmark.testMethod1 avgt 30 19273,717 ± 235,547 ns/op MyBenchmark.testMethod2 avgt 30 71079,139 ± 2686,136 ns/op MyBenchmark.testMethod3 avgt 30 18307,368 ± 202,520 ns/op MyBenchmark.testMethod4 avgt 30 68898,278 ± 2488,104 ns/op

修改

我改写了这个问题,并与更多的precise基准回答它,因为它建议。创建长度为N个新阵列和重复给定阵列

更多推荐

重复一个数组元素

本文发布于:2023-11-30 20:51:58,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1651435.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:数组   元素

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!