剑指 Offer 45. 把数组排成最小的数(中等)

思路:

实际上就是排序,将数组排好序,然后一个个接到StringBuilder中

方法一:自定义双边快速排序

方法二:重写Arrays.sort()方法,该方法本质也是一个快排

方法三:小顶堆(小的在堆顶)

 

代码:

方法一:

class Solution {
    public String minNumber(int[] nums) {
		StringBuilder res=new StringBuilder();
		
		String[] str=new String[nums.length];
		int i=0;
		//将数字变为字符
		for(int num:nums){
			str[i++]=String.valueOf(num);
		}
		
		QuickSort(str,0,nums.length-1);
		for(String s:str){
			res.append(s);
		}
		return res.toString();
    }
	
	private void QuickSort(
		String[] str,
		int l,
		int r
	){
        if(l>=r){
            return;
        }
		int i=l,j=r;
		while(i<j){
			//以str[l]为基准,找到比str[l]小的str[j]
			while(i<j&&(str[j]+str[l]).compareTo(str[l]+str[j])>=0) j--;
			//以str[l]为基准,找到比str[l]大的str[i]
			while(i<j&&(str[i]+str[l]).compareTo(str[l]+str[i])<=0) i++;
			swap(str,i,j);
		}
		swap(str,i,l);
		QuickSort(str,l,i-1);
        QuickSort(str,i+1,r);
	}
	
	private void swap(
		String[] str,
		int i,
		int j
	){
		String temp=str[i];
		str[i]=str[j];
		str[j]=temp;
	}
}

方法二:

class Solution {
    public String minNumber(int[] nums) {
		StringBuilder res=new StringBuilder();
		
		String[] str=new String[nums.length];
		int i=0;
		//将数字变为字符
		for(int num:nums){
			str[i++]=String.valueOf(num);
		}
		
		Arrays.sort(str,(a,b)->(a+b).compareTo(b+a));
		
		for(String s:str){
			res.append(s);
		}
		return res.toString();
    }
}

方法三:

class Solution {
    public String minNumber(int[] nums) {
		StringBuilder res=new StringBuilder();
		
		String[] str=new String[nums.length];
		int i=0;
		//将数字变为字符
		for(int num:nums){
			str[i++]=String.valueOf(num);
		}
		
		PriorityQueue<String> queue=new PriorityQueue<>(new Comparator<String>(){
			public int compare(String a,String b){
				return (a+b).compareTo(b+a);
			}
		});
		
		for(String s:str){
			queue.add(s);
		}
		
		while(!queue.isEmpty()){
			res.append(queue.poll());
		}
		
		return res.toString();
    }
}

 

分解:

1)需要先把int[]数组变为字符串数组

for(int num:nums){
	str[i++]=String.valueOf(num);
}

2)重写Arrays.sort()方法:

Arrays.sort(str,(a,b)->(a+b).compareTo(b+a));

3)定义一个优先队列,重写比较器:

(a+b).compareTo(b+a)相当于(a+b)<(b+a)

返回较小值

PriorityQueue<String> queue=new PriorityQueue<>(new Comparator<String>(){
	public int compare(String a,String b){
		return (a+b).compareTo(b+a);
	}
});

 

复杂度分析:

方法一、二:

    时间复杂度:O(NlogN) 快排的平均时间复杂度就是O(NlogN)

    空间复杂度:O(N) 需要str字符串数组存储N个字符串的额外空间

 

方法三:

    时间复杂度:O(logN) 插入N个元素

    空间复杂度:O(N) N个元素都要插入优先队列

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值