题目】

输入一个正整数数组,将它们连接起来排成一个数,输出能排出的所有数字中最小的一个。例如输入数组{3,32,  321},则输出这两个能排成的最小数字321323。请给出解决问题的算法,并证明该算法。

【思路】

先将整数数组转为字符串数组,然后字符串数组进行排序,最后依次输出字符串数组即可。这里注意的是字符串的比较函数需要重新定义,不是比较a和b,而是比较ab与 ba。如果ab < ba,则a < b;如果ab > ba,则a > b;如果ab = ba,则a = b。比较函数的定义是本解决方案的关键。

结论:如果a < b,那么a排在b前面,否则b排在a前面,这样组成的数字是最小的。

【证明】

如何证明?

证明比较两个数字大小规则是有效的。

证明根据这种规则组合的数字是最小的。

【证明1】

1.证明比较两个数字大小规则是有效的。

一个有效的比较需要三个条件:

(1)自反性,即a等于a;

(2)对称性,即如果a大于b,则b小于a;

(3)传递性,即如果a小于b,b小于c,则a小于c。

现在分别予以证明。

(1)自反性。显然有aa=aa,所以a等于a。

(2)对称性。如果a小于b,则ab<ba,所以ba>ab。因此b大于a。

(3)传递性。 如果a小于b,则ab<ba;如果b小于c,则bc<cb。

举个例子a=1,b=23,c=345。

设a、b、c用十进制表示的时候分别为x位、y位、z位。则ab= a×10y+b,ba=b×10x+a;

则由ab<ba推出a×10y+b< b×10x+a,即a/(10x-1)<b/(10y -1)【结果1】。

同理由bc<cb推出b×10z+c< c×10y+b,即b/(10y-1)<c/(10z -1)【结果2】。

由【结果1】和【结果2】得到a/(10x-1)< c/(10z -1)【结果3】。由【结果3】得到ac<ca,即a小于c。

【证明2】

2.证明根据这种规则组合的数字是最小的。

我们把n个数按照前面的排序规则排好顺序之后,表示为F(n)=A1A2A3…An,则F(n)一定是最小的。

反证法证明:

假设这样排出来的两个数并不是最小的。即至少存在两个x和y(1<=x<y<=n),交换第x个数和地y个数后,使得A1A2…Ay…Ax…An<A1A2…Ax…Ay…An【原结论】。

设F(n)= A1A2…Ax…Ay…An。

因为Ay-1Ay<AyAy-1,则F(n)= A1A2…Ax…Ay…An< A1A2…AxAx+1…AyAy-1…An。同理不断将Ay左移,得到F(n)< A1A2…AyAxAx+1…Ay-2Ay-1…An。

因为AxAx+1<Ax+1Ax,则F(n)< A1A2…AyAx+1AxAx+2…Ay-2Ay-1…An。同理不断将Ax右移,得到F(n)< A1A2…AyAx+1Ax+2…Ay-2Ay-1Ax…An。

即F(n)=A1A2…Ax…Ay…An<A1A2…Ay…Ax…An【新结论】。

【新结论】与【原结论】相矛盾,所以假设不成立,原结论正确,即把n个数按照前面的排序规则排好顺序之后,表示为F(n)=A1A2A3…An,则F(n)一定是最小的。

代码】

 C++ Code 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
 
#include <iostream> // cin cout
#include <string> // string
#include <sstream> // stringstream
#include <algorithm> // sort
using namespace std;

bool compare(const string &str1, const string &str2)
{
    string s1 = str1 + str2;
    string s2 = str2 + str1;
    return s1 < s2;
}

void SortArrayToMinValue(int *data, int length)
{
    )
        return;
    string *strData = new string[length];
    //convert int to string
; i < length; ++i)
    {
        stringstream ss;
        ss << data[i];
        ss >> strData[i];
    }
    // sort string array with user-defined compare function
    sort(strData, strData + length, compare);

// print string array
; i < length; i++)
    {
        cout << strData[i];
    }
    cout << endl;

// free memory
    delete []strData;
    strData = NULL;
}

void test_case()
{
    };
    int length = sizeof(data) / sizeof(int);
    SortArrayToMinValue(data, length);

};
    int length2 = sizeof(data2) / sizeof(int);
    SortArrayToMinValue(data2, length2);
}

int _tmain(int argc, _TCHAR *argv[])
{
    test_case();
    ;
}

【参考】

http://zhedahht.blog.163.com/blog/static/25411174200952174133707/

http://www.cnblogs.com/youxin/p/3294154.html

http://blog.csdn.net/wuzhekai1985/article/details/6704902

41.把数组排成最小的数[Sort array to smallest value]的更多相关文章

  1. 把数组排成最小的数/1038. Recover the Smallest Number

    题目描述 输入一个正整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个.例如输入数组{3,32,321},则打印出这三个数字能排成的最小数字为321323.   Give ...

  2. 九度OJ 1504 把数组排成最小的数【算法】-- 2009年百度面试题

    题目地址:http://ac.jobdu.com/problem.php?pid=1504 题目描述: 输入一个正整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个.例如 ...

  3. 《剑指offer》— JavaScript(32)把数组排成最小的数

    把数组排成最小的数 题目描述 输入一个正整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个.例如输入数组{3,32,321},则打印出这三个数字能排成的最小数字为3213 ...

  4. 剑指Offer - 九度1504 - 把数组排成最小的数

    剑指Offer - 九度1504 - 把数组排成最小的数2014-02-06 00:19 题目描述: 输入一个正整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个.例如输 ...

  5. 剑指Offer:把数组排成最小的数【45】

    剑指Offer:把数组排成最小的数[45] 题目描述 输入一个正整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个.例如,输入数组是{3.32.321},则打印出来的这3 ...

  6. leetcode 179. Largest Number 、剑指offer33 把数组排成最小的数

    这两个题几乎是一样的,只是leetcode的题是排成最大的数,剑指的题是排成最小的 179. Largest Number a.需要将数组的数转换成字符串,然后再根据大小排序,这里使用to_strin ...

  7. php实现把数组排成最小的数(核心是排序)(看别人的代码其实也没那么难)(把php代码也看一下)(implode("",$numbers);)(usort)

    php实现把数组排成最小的数(核心是排序)(看别人的代码其实也没那么难)(把php代码也看一下)(implode("",$numbers);)(usort) 一.总结 核心是排序 ...

  8. 力扣 - 剑指 Offer 45. 把数组排成最小的数

    题目 剑指 Offer 45. 把数组排成最小的数 思路1 将整数数组转化成字符串数组 然后使用Arrays工具类的sort方法帮助我们排序 代码 class Solution { public St ...

  9. 把数组排成最小的数 牛客网 剑指Offer

    把数组排成最小的数 牛客网 剑指Offer 题目描述 输入一个正整数数组,把数组里所有数字拼接起来排成一个数,打印能拼接出的所有数字中最小的一个.例如输入数组{3,32,321},则打印出这三个数字能 ...

随机推荐

  1. 小菜鸟学 MQ(一)

    第一步: 从http://activemq.apache.org/ 下载相关文件. apache-activemq-5.8.0-bin.zip 解压到指定目录下. 第二步: cmd 下切换到   mq ...

  2. Java设计模式-单例模式(Singleton)

    单例对象(Singleton)是一种常用的设计模式.在Java应用中,单例对象能保证在一个JVM中,该对象只有一个实例存在.这样的模式有几个好处: 1.某些类创建比较频繁,对于一些大型的对象,这是一笔 ...

  3. Windows Management Instrumentation WMI Security Technology Learning

    目录 . 引言 . WMI(Windows Management Instrumentation)简介 . 基于WMI的攻击向量 . WMI编程示例 0. 引言 在进行服务器主机的入侵检测.安全攻防的 ...

  4. 简单了解Hibernate核心API

    一.SessionFactory 1.它代表的是数据库的连接,其实就是在hibernate.cfg.xml文件中的配置信息 2.可以预定义SQL语句 3.SessionFactory是线程安全的,它维 ...

  5. html标签页图标

    在head标签加入如下内容: <!--可以在收藏夹中显示出图标--> <link rel="Bookmark" type="image/png" ...

  6. gcc/g++ 参数

    -static  此选项将禁止使用动态库,所以,编译出来的东西,一般都很大,也不需要什么 动态连接库,就可以运行. -share  此选项将尽量使用动态库,所以生成文件比较小,但是需要系统由动态库.

  7. xss之全面剖析

    XSS 全称(Cross Site Scripting) 跨站脚本攻击, 是Web程序中最常见的漏洞.指攻击者在网页中嵌入客户端脚本(例如JavaScript), 当用户浏览此网页时,脚本就会在用户的 ...

  8. spring mvc静态资源文件的引用

    在页面的<title>下 <link rel="stylesheet" href="<%=request.getContextPath()%> ...

  9. 使用guava带来的方便

    ​    ​guava是在原先google-collection 的基础上发展过来的,是一个比较优秀的外部开源包,最近项目中使用的比较多,列举一些点.刚刚接触就被guava吸引了... ​    ​这 ...

  10. Java中Comparable和Comparator实现对象比较

    1.通过Comparable实现排序 package Comparable; import java.util.Arrays; public class ComparableUser implemen ...