如何在Java中以更优化的方式生成数字组合?
我有一个问题陈述,要求将3个不同的数字传递给一个方法,并检查哪3个数字满足某个约束 这是我的代码,但我想知道有没有更优化的方法来检查哪组三元组满足某个约束,而不是创建嵌套循环如何在Java中以更优化的方式生成数字组合?,java,numbers,combinations,triplet,Java,Numbers,Combinations,Triplet,我有一个问题陈述,要求将3个不同的数字传递给一个方法,并检查哪3个数字满足某个约束 这是我的代码,但我想知道有没有更优化的方法来检查哪组三元组满足某个约束,而不是创建嵌套循环 import java.util.ArrayList; import java.util.List; import java.util.Scanner; public class Solution { static List l = new ArrayList(); static int geomet
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class Solution
{
static List l = new ArrayList();
static int geometricTrick(String s)
{
int count = 0;
for (int i = 0; i < s.length(); i++)
{
for (int j = 0; j < s.length(); j++)
{
for (int k = 0; k < s.length(); k++)
{
if (is1stConstraintTrue(s, i, j, k) && is2ndConstraintTrue(i, j, k))
{
l.add(new Triplet(i, j, k));
}
}
}
}
count = l.size();
return count;
}
static boolean is2ndConstraintTrue(int i, int j, int k)
{
boolean retVal = false;
double LHS = Math.pow((j + 1), 2);
double RHS = (i + 1) * (k + 1);
if (LHS == RHS)
retVal = true;
else
retVal = false;
return retVal;
}
static boolean is1stConstraintTrue(String s, int i, int j, int k)
{
boolean retVal = false;
char[] localChar = s.toCharArray();
if (localChar[i] == 'a' && localChar[j] == 'b' && localChar[k] == 'c')
{
retVal = true;
}
return retVal;
}
static class Triplet
{
public int i, j, k;
public Triplet(int i, int j, int k)
{
this.i= i;
this.j= j;
this.k= k;
}
}
public static void main(String[] args)
{
Scanner in = new Scanner(System.in);
int n = in.nextInt();
String s = in.next();
int result = geometricTrick(s);
System.out.println(result);
}
}
import java.util.ArrayList;
导入java.util.List;
导入java.util.Scanner;
公共类解决方案
{
静态列表l=新的ArrayList();
静态整数几何单击(字符串s)
{
整数计数=0;
对于(int i=0;i
以下是一些提示:
pow
String::toCharray()
非常昂贵。它将所有字符复制到一个新数组中。每次你叫它。不要叫它多次Triple
实例。数一数为您提供一个简单而“愚蠢”的解决方案,不使用这些内部循环 让我们使用类似于
迭代器的工厂。这将使用条件语句“隐藏”循环
public class TripletFactory{
final int maxI, maxJ, maxK;
int i, j ,k;
public TripletFactory(int i, int j, int k){
this.maxI = i;
this.maxJ = j;
this.maxK = k;
}
public Triplet next(){
if(++k > maxK){
k = 0;
if(++j > maxJ){
j = 0;
if(++i > maxI){
return null;
}
}
}
return new Triplet(i,j,k);
}
}
这样,您只需在一个循环中获得一个新的三元组
,直到null
实例
TripletFactory fact = new TripletFactory(2, 3 ,5);
Triplet t = null;
while((t = fact.next()) != null){
System.out.println(t);
}
//no more Triplet
你想怎么用就怎么用
然后,您必须更新约束方法,以获取一个三元组
,并使用getter检查实例
这可能是一种Triplet
的方法,让它顺便验证自己
注:
我使用了与迭代器
相同的符号,因为我们可以实现迭代器
和Iterable
来使用如下符号:
for(Triplet t : factory){
...
}
您介绍的简单方法具有立方时间复杂性(对于
-循环有三个嵌套的)。如果您的输入中多次出现'a'
、'b'
和'c'
,那么首先确定所有'a'
、'b'
和'c'
的索引,然后仅在该集合上检查第二个条件可能是值得的
import java.util.ArrayList;
import java.util.List;
public class Main {
public static List<Integer> getAllOccurrences(String input, char of) {
List<Integer> occurrences = new ArrayList<Integer>();
char[] chars = input.toCharArray();
for (int idx = 0; idx < chars.length; ++idx) {
if (of == chars[idx]) {
occurrences.add(idx);
}
}
return (occurrences);
}
static List<Triplet> geometricTrick(String input){
List<Integer> allAs = getAllOccurrences(input, 'a');
List<Integer> allBs = getAllOccurrences(input, 'b');
List<Integer> allCs = getAllOccurrences(input, 'c');
List<Triplet> solutions = new ArrayList<Triplet>();
// reorder the loops, so that the c-loop is the innermost loop (see
// below why this is useful and how it is exploited).
for (int a : allAs) {
for (int c : allCs) {
// calculate lhs as soon as possible, no need to recalculate the
// same value multiple times
final int lhs = ((a + 1) * (c + 1));
for (int b : allBs) {
final int rhs = ((b + 1) * (b + 1));
if (lhs > rhs) {
continue;
}
/* else */ if (lhs == rhs) {
solutions.add(new Triplet(a, b, c));
}
// by construction, the b-values are in ascending or der.
// Thus if the rhs-value is larger or equal to the
// lhs-value, we can skip all other rhs-values. for this
// lhs-value.
// if (lhs <= rhs) {
break;
// }
}
}
}
return (solutions);
}
static class Triplet {
public final int i;
public final int j;
public final int k;
public Triplet(int i, int j, int k) {
this.i = i;
this.j = j;
this.k = k;
}
}
}
import java.util.ArrayList;
导入java.util.List;
公共班机{
公共静态列表getAllOccurrences(字符串输入,字符){
列表出现次数=新建ArrayList();
char[]chars=input.toCharArray();
对于(int idx=0;idx右侧){
持续
}
/*else*/if(lhs==rhs){
添加(新的三联体(a,b,c));
}
//通过构造,b值以升序或降序排列。
//因此,如果rhs值大于或等于
//lhs值,我们可以跳过所有其他rhs值
//lhs值。
//如果(lhs您的满意度标准是什么?double
比较不好。将其更改回int
。这看起来像是一个双重问题。首先,您要查找输入中的字符'a'
、'b'
和'c'
。接下来,您想知道字符所在的索引是否满足某些c要求条件。我将首先查找所有出现的'a'
,'b'
和'c'字符串
并检查每个三元组