求非負(fù)元素數(shù)組所有元素能組合的最大字符串

原文:https://www.fanhaobai.com/2017/04/array-form-max-string.html

問題敘述:將一個非負(fù)元素數(shù)組中的所有元素排列組合在一起嗡呼,找出值最大的那個排列情況岳颇。例如 [0, 9, 523, 94, 10, 4]议经,排列組合后值最大數(shù)為:9945234100忍捡。

本文廢話較多简珠,可以直接跳轉(zhuǎn)到 編碼實現(xiàn) 部分担敌。

背景描述

這是我遇到的一道筆試題崎淳。首次遇見我也是很懵扔亥,當(dāng)時我的第一感覺就是排序斜做,但是沒有及時理清里面的規(guī)律苞氮,導(dǎo)致后面并沒有解答出此題。

問題分析

確定輸入值

該問題描述很簡單瓤逼,也給出了測試用例笼吟,需求很明白库物。但是還需要注意問題背后隱藏的一些問題。

可確定輸入的情況大致為:

  • 數(shù)組元素都為非負(fù)數(shù)贷帮,但可能為 0戚揭;
  • 數(shù)組長度并沒有確定,長度可能很大撵枢。這里假設(shè)操作不溢出民晒;
  • 數(shù)組元素的位數(shù)不確定,用例只涉及到 2 位數(shù)锄禽,需要考慮多位數(shù)的情況潜必。這里假設(shè)操作不溢出;

尋找規(guī)律

面試時請教了一下面試官沃但,面試官的思路:

最簡單辦法就是枚舉所有可能的排列組合情況磁滚,然后求排列組合后的最大值;再就是尋找組合的規(guī)律宵晚,滿足什么條件的元素排列在前垂攘。

當(dāng)然這只是面試官提供的一些解決思路,付諸于實踐還需要探索淤刃。在復(fù)試前的一天晚上我再次翻出這個問題晒他,并找到了一些思路。

就拿問題中的用例 [0, 9, 523, 94, 10, 4] 來說逸贾,需要找出的結(jié)果為:9,94,523,4,10,0(為了方便說明陨仅,用”,“分割了數(shù)組元素)。

先將復(fù)雜問題簡單化處理耕陷,首先嘗試使用 排序算法 來分析過程掂名。分析 9 和 94 的排列,為什么 9 排列在 94 前哟沫?那是因為這 2 個數(shù)存在 2 種排列情況饺蔑,既_ 9_94_ 和_ 9_49_,很明顯 9_94 排列大于 9_49 排列嗜诀,所以需要將 9 排列在 94 前猾警,反之則需要交換元素位置。如果采用這樣規(guī)則處理隆敢,是在 2 個元素之間進行枚舉排列情況发皿,且單次枚舉情況限定在了 2 種,降低了問題的復(fù)雜程度并易于編碼實現(xiàn)拂蝎,后續(xù)可以直接使用排序方法來多次重復(fù)這種 2 個元素之間的單次枚舉動作穴墅。

說明:符號“_”為占位符,表示該位置可能還存在其他元素,但不影響當(dāng)前兩個元素的前后排列順序玄货。后續(xù)出現(xiàn)該符號將不再說明皇钞。

總之,我認(rèn)為該問題是排序問題的一個變種情況松捉,同排序問題不同的是 比較規(guī)則夹界。這里不是直接比較 2 個元素值大小,而是比較 2 個元素排列組合后值的大小隘世。

實現(xiàn)思路

經(jīng)過上述分析可柿,問題規(guī)律已經(jīng)掌握清楚,這里整理出實現(xiàn)的思路丙者。

整體思路

  • 確定使用排序算法實現(xiàn)复斥;
  • 與傳統(tǒng)排序不同之處為元素之間的比較規(guī)則;

排序過程

使用冒泡排序來說明上述用例的排序過程蔓钟。

{% asset_img 65FD0FD202413415D266AC754A75AAF3.png %}

比較規(guī)則

本問題的排序比較規(guī)則可以描述為:假設(shè)參與比較的兩個元素為 A永票、B(初始時 A 在 B 前,排序結(jié)果從左至右為由大到欣哪),比較時如果排列 A_B 小于排列 B_A键俱,A 和 B 則交換位置兰绣,反之不交換。

編碼實現(xiàn)

比較規(guī)則

/**
 * 比較規(guī)則
 * @param   string    $a
 * @param   string    $b
 * @return  int
 */
function cmp($a, $b) {
    if ($a == $b) {
        return 0;
    }
    return $a . $b > $b . $a ? -1 : 1;
}

冒泡排序

/**
 * 冒泡排序
 * @param   array    $Arr   待排序數(shù)組
 * @return  array
 */
function bubble_sort(array $Arr) {
    $length = count($Arr);
    for ($i = 1, $change = true; $i <= $length && $change; $i++) {
        $change = false;
        for ($j = $length - 1; $j > $i - 1; $j--) {
            if (cmp($Arr[$j - 1], $Arr[$j]) > 0) {
                $temp = $Arr[$j - 1];
                $Arr[$j - 1] = $Arr[$j];
                $Arr[$j] = $temp;
                $change = true;
            }
        }
    }
    return $Arr;
}

/**
 * 尋找非零元素數(shù)組中所有元素排列組合后的最大值
 * @param   array     $Arr        待排序數(shù)組
 * @param   string    $method     排序方法
 * @return  mixed
 */
function array_form_max_str(array $Arr, $method = 'bubble') {
    //參數(shù)校驗
    if (!is_array($Arr)) return false;
    foreach ($Arr as $value) {
        if ($value < 0) return false;
    }
    //排序算法
    switch ($method) {
        case 'quick' :
            usort($Arr, "cmp");           //快速排序
            break;
        case 'bubble' :
            $Arr = bubble_sort($Arr);     //冒泡排序
            break;
        default : break;
    }
    //拼接
    return implode('', $Arr);
}

快速排序

由于 PHP 中 sort 排序函數(shù)采用快速排序算法编振,這里直接使用之缀辩。

/**
 * 尋找非零元素數(shù)組中所有元素排列組合后的最大值
 * @param   array     $Arr        待排序數(shù)組
 * @param   string    $method     排序方法
 * @return  mixed
 */
function array_form_max_str(array $Arr, $method = 'quick') {
    //參數(shù)校驗
    if (!is_array($Arr)) return false;
    foreach ($Arr as $value) {
        if ($value < 0) return false;
    }
    //排序算法
    switch ($method) {
        case 'quick' :                   //快速排序
            usort($Arr, "cmp");
            break;
        case 'bubble' :
            $Arr = bubble_sort($Arr);    //冒泡排序
            break;
        default : break;
    }
    //拼接
    return implode('', $Arr);
}

用例測試

這里只對快速排序方法使用 2 組測試用例并列舉如下。

測試代碼

$Arr = [];
echo '數(shù)組為[', implode(',', $Arr), ']', PHP_EOL;
echo '最大排列組合為:', array_form_max_str($Arr), PHP_EOL;

測試結(jié)果

//第1組用例
數(shù)組為[0,9,523,94,10,4]
最大排列組合為:9945234100

//第2組用例
數(shù)組為[20,913,223,91,20,3]
最大排列組合為:9191332232020

寫在最后

經(jīng)過深入分析問題的本質(zhì)踪央,也使得我對與排序算法有了更深入的認(rèn)識臀玄,更算是一個鞏固。同時畅蹂,正是由于我嘗試著去解決這個問題健无,才使得我在后面的復(fù)試環(huán)節(jié)中面試官再次提出相同問題時,給出了一個滿意的解決方案液斜。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末累贤,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子少漆,更是在濱河造成了極大的恐慌臼膏,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,490評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件示损,死亡現(xiàn)場離奇詭異渗磅,居然都是意外死亡,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,581評論 3 395
  • 文/潘曉璐 我一進店門始鱼,熙熙樓的掌柜王于貴愁眉苦臉地迎上來仔掸,“玉大人,你說我怎么就攤上這事风响〖翁” “怎么了?”我有些...
    開封第一講書人閱讀 165,830評論 0 356
  • 文/不壞的土叔 我叫張陵状勤,是天一觀的道長鞋怀。 經(jīng)常有香客問我,道長持搜,這世上最難降的妖魔是什么密似? 我笑而不...
    開封第一講書人閱讀 58,957評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮葫盼,結(jié)果婚禮上残腌,老公的妹妹穿的比我還像新娘。我一直安慰自己贫导,他們只是感情好抛猫,可當(dāng)我...
    茶點故事閱讀 67,974評論 6 393
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著孩灯,像睡著了一般闺金。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上峰档,一...
    開封第一講書人閱讀 51,754評論 1 307
  • 那天败匹,我揣著相機與錄音,去河邊找鬼讥巡。 笑死掀亩,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的欢顷。 我是一名探鬼主播槽棍,決...
    沈念sama閱讀 40,464評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼吱涉!你這毒婦竟也來了刹泄?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,357評論 0 276
  • 序言:老撾萬榮一對情侶失蹤怎爵,失蹤者是張志新(化名)和其女友劉穎特石,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體鳖链,經(jīng)...
    沈念sama閱讀 45,847評論 1 317
  • 正文 獨居荒郊野嶺守林人離奇死亡姆蘸,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,995評論 3 338
  • 正文 我和宋清朗相戀三年墩莫,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片逞敷。...
    茶點故事閱讀 40,137評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡狂秦,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出推捐,到底是詐尸還是另有隱情裂问,我是刑警寧澤,帶...
    沈念sama閱讀 35,819評論 5 346
  • 正文 年R本政府宣布牛柒,位于F島的核電站堪簿,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏皮壁。R本人自食惡果不足惜椭更,卻給世界環(huán)境...
    茶點故事閱讀 41,482評論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望蛾魄。 院中可真熱鬧虑瀑,春花似錦、人聲如沸滴须。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,023評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽扔水。三九已至把夸,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間铭污,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,149評論 1 272
  • 我被黑心中介騙來泰國打工膀篮, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留嘹狞,地道東北人。 一個月前我還...
    沈念sama閱讀 48,409評論 3 373
  • 正文 我出身青樓誓竿,卻偏偏與公主長得像磅网,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子筷屡,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,086評論 2 355

推薦閱讀更多精彩內(nèi)容

  • 數(shù)組在程序設(shè)計中涧偷,為了處理方便, 把具有相同類型的若干變量按有序的形式組織起來毙死。這些按序排列的同類數(shù)據(jù)元素的集合稱...
    朱森閱讀 3,933評論 2 13
  • 第5章 引用類型(返回首頁) 本章內(nèi)容 使用對象 創(chuàng)建并操作數(shù)組 理解基本的JavaScript類型 使用基本類型...
    大學(xué)一百閱讀 3,237評論 0 4
  • 問答題47 /72 常見瀏覽器兼容性問題與解決方案燎潮? 參考答案 (1)瀏覽器兼容問題一:不同瀏覽器的標(biāo)簽?zāi)J(rèn)的外補...
    _Yfling閱讀 13,754評論 1 92
  • LeetCode 刷題隨手記 - 第一部分 前 256 題(非會員),僅算法題扼倘,的吐槽 https://leetc...
    蕾娜漢默閱讀 17,793評論 2 36
  • 1. 在年少的時候颜曾,你是否幻想過幸福的模樣。 2. 希望每一天都能過的精彩秉剑。 3. 總是希望能找到自己想象之中的愛...
    e19c0228dcb3閱讀 527評論 0 0