`
java--hhf
  • 浏览: 308713 次
  • 性别: Icon_minigender_1
社区版块
存档分类
最新评论

byte用于数字排序

阅读更多

【问题】
    对一百万个不相同的数字进行排序,要求时间复杂度O(1),空间复杂度尽可能小!
【分析】
    大数据的排序问题,首选方法是“归并”,之前我也写过十亿个数的归并排序算法,且在此基础上的优化方案——大范围内归并小范围内插入排序等等,但本文有一个时间复杂度的要求,归并排序的时间复杂度是O(nlgn),因此我们尝试一种新闻排序算法——“bit排序法”。
    “bit排序法”——待排序的数作为bit位的下标,当前位置的bit置为1,一轮遍历待排序数之后,打印出所有当前数值为1的数字下标。
    最小的数据结构单位是byte,因此处理起来稍微麻烦了一点
【代码】

package com.hhf;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
/**
 * bit排序法
 * @author HHF
 * 2015年11月17日17:12:37
 * @version 1.0 只支持不同数据的排序
 */
public class PhoneNumSort {

	private static String path = "E:/phoneNum.txt";
	private static String resultPath = "E:/phoneNumResult.txt";
	
	private int size = 1000000;
	public static void main(String[] args) {
		PhoneNumSort phoneNumSort = new PhoneNumSort();
		//生成不相同的一百万个数
		phoneNumSort.createNumber(phoneNumSort.size);
		//统计排序数大小
		int bitSize = phoneNumSort.countLineSize(path);
		//用来保存数据--数组的下标为n,表示数据为8*(n-1)+k
		byte[] byteData = new byte[bitSize/8 + 1];
		phoneNumSort.setByteData(byteData);
	}
	/**
	 * 读取文件,并将文件中数值对应到byte类型的打他中去
	 * @param byteData
	 */
	private void setByteData(byte[] byteData){
		int index = 0;
		int n = 0;//第几行
		int k = 0;//第几位
		try {
			BufferedReader br = new BufferedReader(new FileReader(path));
			String str = br.readLine();
			while(str!=null){
				index = new Integer(str);//bit中的下标
				n = index/8;
				k = index%8;
				//设置当前位置的值为1
				byteData[n] += getAddNum(k);  
				str = br.readLine();
			}
			br.close();
			StringBuffer content = new StringBuffer();
	        for(int i=byteData.length-1; i>-1; i--){
	        	if(byteData[i]>=128){
	        		byteData[i] -= 128;
	        		content.append(8*i + 8).append("\n");
	        	}
	        	if(byteData[i]>=64){
	        		byteData[i] -= 64;
	        		content.append(8*i + 7).append("\n");
	        	}
	        	if(byteData[i]>=32){
	        		byteData[i] -= 32;
	        		content.append(8*i + 6).append("\n");
	        	}
	        	if(byteData[i]>=16){
	        		byteData[i] -= 16;
	        		content.append(8*i + 5).append("\n");
	        	}
	        	if(byteData[i]>=8){
	        		byteData[i] -= 8;
	        		content.append(8*i + 4).append("\n");
	        	}if(byteData[i]>=4){
	        		byteData[i] -= 4;
	        		content.append(8*i + 3).append("\n");
	        	}
	        	if(byteData[i]>=2){
	        		byteData[i] -= 2;
	        		content.append(8*i + 2).append("\n");
	        	}
	        	if(byteData[i]>=1){
	        		content.append(8*i + 1).append("\n");
	        	}
	        }
	        storeDataToFile(resultPath, content.toString().getBytes());
	        System.out.println(System.currentTimeMillis()+"--排序结果已经写入文件");
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
	/**
	 * 获得每个位置上对应应该要加的数值
	 * @param pos 位置
	 * @return 返回该位置对应的数
	 */
	private int getAddNum(int pos){
		if(pos>0 && pos<9){
			return 1<<(pos-1);
		}else{
			return 0;
		}
	}
	
	/**
	 * 读取文章的行数
	 * @param path 文件路径
	 * @return size 数据量
	 */
	private int countLineSize(String path){
		int count = 0;
		try {
			BufferedReader br = new BufferedReader(new FileReader(path));
			String str = br.readLine();
			while(str!=null){
				count++;
				str = br.readLine();
			}
			br.close();
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
		System.out.println(System.currentTimeMillis()+"--待排序的数据量是"+count);
		return count;
	}
	/** 
     * 生成指定数量的数据 
     * @param path 文件的路径 
     * @param size 数据数量 
     */  
    private void createNumber(int size){//还是需要先 定义InputStream输入流对象    
    	if(size < 1){
    		return;
    	}
        StringBuffer content = new StringBuffer();
        for(int i=1; i<=size; i++){
        	content.append(i).append("\n");
        }
        storeDataToFile(path, content.toString().getBytes());  
        System.out.println(System.currentTimeMillis()+"--文件创建结束  共生成了数据 "+size+" 条");  
    }
    
    /**
     * 将数据存储到文件中
     * @param path
     * @param content
     */
    private void storeDataToFile(String path, byte[] content){
    	File file = new File(path);
    	if(!file.exists()){
    		try {
				file.createNewFile();
			} catch (IOException e) {
				e.printStackTrace();
			}
    	}
    	try {
			java.io.OutputStream os = new java.io.FileOutputStream(path);
			java.io.BufferedOutputStream bos = new java.io.BufferedOutputStream(os);  
	        bos.write(content);
	        bos.flush();// 将缓冲区中的内容强制全部写入到文件中(不管是否已经全部写入)有点类似于下面的语句  
	        bos.close();  
	        os.close();
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
    }
}

 

--------相关推荐文章--------- 

《10亿个字符串的排序问题》http://java--hhf.iteye.com/admin/blogs/2166129
《大范围归并小范围插入排序》http://java--hhf.iteye.com/admin/blogs/2163465

0
1
分享到:
评论

相关推荐

    DataTable 存储byte数组

    `byte[]`(或称字节数组)是一种用于存储一系列字节的数据类型。在许多应用场景中,`byte[]` 被用来表示图像、音频文件、加密数据或其他任何形式的二进制数据。由于其灵活性,`byte[]` 成为了在应用程序中处理二进制...

    Radix Sort (基数排序)排序算法

    ### Radix Sort (基数排序) 排序算法详解 ...此外,基数排序不适合小规模数据排序,因为其初始化和管理桶的成本较高。 综上所述,基数排序是一种高效稳定的排序算法,在特定场景下能够提供优秀的性能表现。

    易语言字节型数组排序

    其次,排序算法是计算机科学中的重要概念,它用于将一组数据按照特定顺序排列。在易语言中,对字节型数组进行排序,常见的算法有冒泡排序、选择排序、插入排序、快速排序等。每种算法都有其优缺点,适用于不同的场景...

    mips汇编语言实现选择排序(字符串形式输入)

    - 适合于小型数组或教学用途,但对于大规模数据排序效率较低。 3. **字符串处理**: - 在MIPS汇编语言中,字符串通常作为ASCII字符数组处理。 - 字符串转换涉及到将ASCII码转换为对应的数值。这通常通过减去数字...

    汇编—人名排序程序的实现

    1. 数据定义:在汇编程序中,首先需要定义数据段来存储待排序的人名。这可以通过`DB`(Define Byte)或`DW`(Define Word)伪指令完成,根据人名的长度和字符编码选择合适的方式。 2. 子程序(函数):为了实现排序...

    商品排序程序设计.txt

    - `endaddr dw`: 结束地址,用于排序过程中的循环条件判断。 - `messg1 db 'Name', '$'`: 提示信息,用于要求用户输入商品名称。 - `messg2 db 'Sort name', 13, 10, '$'`: 排序后的提示信息。 - `namectr db 0`...

    基于Java按位拆分快速排序算法的数值仿真.pdf

    近年来,许多专家学者提出了许多高效的排序算法,如SISⅢ、Byte快速排序、基于统计的排序Ⅲ、比特位拆分索引排序算法等。 基于Java按位拆分快速排序算法的基本思想是:首先根据数据中的比特对数据进行划分整理,将...

    java中的排序.ppt

    简单类型包括 byte, char, short, int, long, float, double 等数据类型。这些类型不能放在聚集中,只能使用数组。Java 中的 Arrays 类提供了对这些类型的 sort 方法,可以用来对简单类型的数组进行排序。例如: ``...

    汇编源代码-冒泡排序

    1. **数据定义**:首先,汇编源代码会定义一个数组,用于存储待排序的数据。这些数据通常用伪指令(如`DB`,Data Byte)来定义,每一项表示一个字节大小的数值。 2. **变量声明**:可能会定义一些辅助变量,如指示...

    汇编语言实现冒泡排序算法

    3. **换行符定义**:用于在输出排序结果后添加换行符。 ##### 函数定义与调用 ```assembly section.text global _start _start: ; 调用冒泡排序算法 call bubble_sort ; 输出排序后的数组 mov eax, 4 ; sys_...

    成绩输入查询排序(JAVA).pdf

    * 整数类型:byte、short、int、long * 浮点数类型:float、double * 字符类型:char * 布尔类型:boolean * 引用类型:String、Array、Vector Java运算符 Java语言提供了多种运算符,包括: * 算术运算符:+、-...

    Java对List对象进行排序_.docx

    在Java编程中,对List对象进行排序是一个常见的需求,尤其是在处理数据集合时。Java提供了一个便捷的方法`Collections.sort()`,可以直接对实现了`Comparable`接口的List进行排序。然而,当需要根据对象内部的某个...

    go语言 排序

    在编程领域,排序是至关重要的一个环节,尤其是在处理大量数据时。Go语言,作为一种现代、高效且并发性能优秀的系统级编程语言,提供了多种排序方法。本文将深入探讨Go语言中的排序算法,包括冒泡排序和快速排序,并...

    大数据处理算法.pdf

    堆排序、快速排序和归并排序是经典的排序算法,它们在大数据处理中用于对数据进行预处理或聚合。堆排序利用堆结构保证在O(n log n)的时间复杂度内完成排序;快速排序则通过分治策略快速划分数据;归并排序则通过合并...

    对象数组练习题.doc

    "JavaSE对象数组练习题" 本资源是一个JavaSE练习题,旨在帮助学习者熟悉Java编程语言的基本概念和对象数组的处理。下面是对该练习题的详细...通过完成这个练习题,学习者可以熟悉Java编程语言的基本语法和数据结构。

    计算机编程面试题集合.pdf

    * 数据存储:Bit 是计算机数据量的最小单位,Byte 是计算机信息技术用于计量存储容量和传输容量的一种计量单位 * 数据类型:了解 Bit 和 Byte 在计算机中的应用 3. 排序算法 知识点: * 数据结构:排序算法的概念...

    简明python教程(A byte of Python)

    这个教程可能涵盖了Python的基本语法,变量,数据类型,控制结构,函数,模块等方面。 【描述】"A byte of Python中文版和部分示例" 指出该教程已经翻译为中文,便于中文用户阅读理解。"部分示例"意味着教程中包含...

    SQL 用于各种数据库的数据类型

    SQL 用于各种数据库的数据类型 Microsoft Access、MySQL 和 SQL Server 所使用的数据类型和范围。 Microsoft Access 数据类型 数据类型 描述 存储 Text 用于文本或文本与数字的组合。最多 255 个字符。 ...

    Java基础编程代码-包含main()、输入输出、基本数据类型、数组、基本排序算法等的代码

    下面将对 Java 基础编程代码进行详解,包括 main() 函数、输入输出、基本数据类型、数组和基本排序算法等。 main() 函数 在 Java 程序中,main() 函数是程序的入口点,是程序执行的开始。main() 函数的定义格式...

Global site tag (gtag.js) - Google Analytics