`

Java高效组合之一

阅读更多
这里有一个问题,取所有1-n组合的时候程序正常,但如果取单一的c(n,m)组合时会有问题。
如取c(20,2)就会内存溢出,但取一个c(20,10)又正常,本人还没明白什么问题,请高手指教。
package stats.hotdeck;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
* 取所有组合的内部类
*
*/
public class Combination {
private int[] index;// 用于存储需要组合的数组的下标的成员变量。
private int length;// 表示待组合数组的长度。
private int n;// 组合序列的元素个数
private long numLeft;// 用于存储剩余组合序列个数的成员变量。可以用double型,如果数量级足够大的话。
// private long total;//用于存储组合序列总数的成员变量。
private int[] intArray;// 存放待组合数组下标的数组。

public Combination(int length) {
this(length, 0);
}

public Combination(int length, int n) {
this.length = length;
this.n = n;
reset();
initIntArray();
}

public void reset() {
if (n > length) {
System.out.println("需要组合的个数超出数组元素个数!");
System.exit(1);
}
// 初始化numLeft,开始时numLeft应该为2^n.
                  // 如果是double,则转型为double,否则会取漏组合
numLeft = (long) Math.pow((double) 2, (double) length);
// 初始化数组index。
index = new int[length];
Arrays.fill(index, 0);
}

private int sum() {
int s = 0;
for (int i = 0; i < index.length; i++) {
s += index[i];
}
return s;
}

public boolean hasMore() {
return numLeft > 0;
}

public int[] getNext() {
index[0] += 1;
for (int i = 0; i < index.length; i++) {
if (index[i] == 2) {
index[i] = 0;
if (i != index.length - 1)
index[i + 1] += 1;
}
}
numLeft--;
if (this.n != 0) {
if (sum() == this.n)
return index;
else if (hasMore())
return getNext();
}
return index;
}

protected int[] getIntArray() {
return intArray;
}
/**
* 按默认的顺序从0开始赋值,初始化intArray
*/
protected void initIntArray() {
this.intArray = new int[this.length];
for (int i = 0; i < this.length; i++) {
intArray[i] = i;
}
}

/**
* 自定义初始化intArray
*/
protected void initIntArray(int[]arr) {
this.intArray=arr;
}

/**
* 得到所有以数组下标为组合的所有组合的集合
* @return
*/
protected List getAllCombination(){
List combList=new ArrayList();
List oneComb=null;
int a=0;
while (hasMore()) {
oneComb=new ArrayList();
int[] index = getNext();
for (int j = 0; j < intArray.length; j++) {
if (index[j] != 0) {
a = intArray[index[j] * j];
oneComb.add(new Integer(a));
}
}
if(!oneComb.isEmpty()){
combList.add(oneComb);
}
}
return combList;
}

/**
* 得到所有以对象元素组合的所有组合的集合
* @param objectList 进行组合的对象集合
* @return
*/
protected List getAllCombinationForObject(List objectList){
List combList=new ArrayList();
List oneComb=null;
int a=0;
while (hasMore()) {
oneComb=new ArrayList();
int[] index = getNext();
for (int j = 0; j < intArray.length; j++) {
if (index[j] != 0) {
a = intArray[index[j] * j];
oneComb.add(objectList.get(a));
}
}
if(!oneComb.isEmpty()){
combList.add(oneComb);
}
}
return combList;
}

public static void main(String[] args){
Combination comb=new Combination(20,10);
List list=comb.getAllCombination();
System.out.print(list.size());
}
}
分享到:
评论

相关推荐

    实现了排列组合算法的类(JAVA).rar

    这个"实现了排列组合算法的类(JAVA).rar"文件提供了一种高效的JAVA实现,可以处理任意类型数组的排列和组合。下面将详细讨论排列组合的基本概念,以及在JAVA中实现这些算法的关键点。 排列是指从n个不同元素中...

    《Java程序设计之网络编程》

    《Java程序设计之网络编程》是一本专注于Java网络编程的教材,它涵盖了网络通信的基础理论以及Java语言在实现网络应用中的各种技术。该资源包括课件和源码,旨在帮助学习者通过实践来深入理解Java网络编程的核心概念...

    Java写的一个数组的中,m个元素的组合问题

    在编程领域,数组是基本的数据结构之一,用于存储一系列同类型的数据。在这个场景中,我们关注的是如何在Java中处理数组中的元素组合问题。数组的组合问题通常涉及到组合数学和算法设计,它可以帮助我们找出所有可能...

    java2D Java Java Java

    这个框架在Sun Microsystems(后被Oracle收购)的程序员们的精心设计下诞生,旨在为Java开发者提供高效、灵活的图形绘制能力,使得应用程序能够呈现高质量的视觉效果。 Java 2D API构建于Java AWT(Abstract Window...

    java 组合包.rar

    Java是世界上最流行的编程语言之一,尤其在企业级应用开发领域占据主导地位。JDK(Java Development Kit)是Java开发的核心工具集,包含了编译器、JRE(Java Runtime Environment)以及各种开发工具。本组合包“java...

    Java-Java函数式编程教程

    Java函数式编程是一种编程范式,它强调使用函数作为程序的基本构建块,将计算视为函数的组合,并且尽可能避免改变状态和可变数据。在Java 8及更高版本中,函数式编程得到了官方的大力支持,引入了Lambda表达式、...

    Java in easy steps Covers Java 9 6th Edition

    其中,“Lambda”作为核心知识点之一,代表了Java语言在现代编程范式中的一大步。 Lambda表达式是一种可以传递给方法或存储在变量中的匿名函数。它允许开发者以更简洁的方式编写代码,特别是当涉及到使用函数式接口...

    Java组合式异步编程CompletableFuture.pdf

    `CompletableFuture`是Java 8中新增的功能之一,它继承自`Future`并实现了`CompletionStage`接口。这使得它可以灵活地处理异步操作和任务间的依赖关系。 ##### 2.1 Future与CompletionStage - **Future**:表示一个...

    java swing漂亮界面(超酷) javaswing教程

    Swing中的事件处理机制也是其重要特性之一。通过监听器接口,如ActionListener、MouseListener等,开发者可以为组件添加事件响应,使得用户与界面的交互更加动态和直观。例如,点击按钮时执行特定的代码,或者当鼠标...

    java之UML类图元素

    类图作为UML中最基本的图表之一,能够清晰地展现类与类之间的关系,以及类的内部结构。以下将详细介绍UML类图中的各种元素及其与Java语言的映射。 1. **类(Class)**:类是UML类图的核心,代表了Java中的类。类包含...

    JAVA核心技术讲解

    首先,Java 8中的核心特性之一是Lambda表达式。这是一种简洁的函数式编程方式,可以用来替代匿名内部类,简化多参数无状态的回调函数,极大地提高了代码的可读性和简洁性。Lambda表达式的引入,使得Java在处理集合...

    java 核心技术 高级部分第10版 java 8 介绍

    在Java 8中,最显著的改变之一是引入了函数式编程概念。Lambda表达式是这一改变的核心,它允许开发者以更简洁、更易读的方式处理函数。Lambda表达式可以作为参数传递,也可以作为返回值,这极大地简化了对集合的操作...

    java技术文档 pdf汇总

    首先,Java是全球最广泛使用的编程语言之一,尤其在企业级应用开发中占据主导地位。Java的特点是“一次编写,到处运行”,它的跨平台能力基于Java虚拟机(JVM)。Java技术文档将详细介绍其语法、类库、面向对象编程...

    浅析C语言、Java、Python的数组合并方法.pdf

    Java作为一种面向对象的语言,其数组合并相对简单。Java提供了内置的方法来合并数组,如System.arraycopy()和java.util.Arrays类。System.arraycopy()方法提供了一种高效的数组元素复制方式,可以用来合并数组,但...

    java学习资料之Java笔记

    Java是一种广泛使用的面向对象的编程语言,以其跨平台、安全性和高效性著称。这篇学习笔记将带你深入了解Java的基础知识,包括它的特点、运行原理以及编程基础。 1. **前言** Java的学习始于理解其核心特性。Java...

    java8官方api帮助文档

    例如 `(int x, int y) -&gt; x + y` 是一个接受两个整数并返回它们之和的Lambda表达式。Lambda可以作为方法参数、返回值,甚至存储在变量中。 2. **函数式接口**: 函数式接口是只有一个抽象方法的接口,可以被Lambda...

    一个Java外卖系统源码.zip

    订单记录是系统的核心功能之一,包括订单创建、支付处理、状态跟踪等。订单数据的处理可能涉及到事务管理,确保数据的一致性。支付部分可能对接第三方支付平台如支付宝、微信支付的SDK,保证交易的安全性。此外,...

    JAVA相关mobi格式电子书

    Spring是Java应用开发中最流行的框架之一,用于构建企业级应用。这本书揭示了Spring框架的内部工作原理,包括依赖注入、AOP(面向切面编程)、数据访问、事务管理等核心特性。掌握Spring技术可以提升开发效率,实现...

Global site tag (gtag.js) - Google Analytics