天天看點

智力題 2014藍橋杯 C/C++ B組 螞蟻感冒

引言

對于算法題,特别是藍橋杯的算法題,coding能力固然是一方面,但是思維方式和思維能力更重要。

藍橋組委推薦的CC150思維是解題的實用思維。

題面

問題描述

  長100厘米的細長直杆子上有n隻螞蟻。它們的頭有的朝左,有的朝右。

每隻螞蟻都隻能沿着杆子向前爬,速度是1厘米/秒。

當兩隻螞蟻碰面時,它們會同時掉頭往相反的方向爬行。

這些螞蟻中,有1隻螞蟻感冒了。并且在和其它螞蟻碰面時,會把感冒傳染給碰到的螞蟻。

請你計算,當所有螞蟻都爬離杆子時,有多少隻螞蟻患上了感冒。

輸入格式

  第一行輸入一個整數n (1 < n < 50), 表示螞蟻的總數。

接着的一行是n個用空格分開的整數 Xi (-100 < Xi < 100), Xi的絕對值,表示螞蟻離開杆子左邊端點的距離。正值表示頭朝右,負值表示頭朝左,資料中不會出現0值,也不會出現兩隻螞蟻占用同一位置。其中,第一個資料代表的螞蟻感冒了。

輸出格式

  要求輸出1個整數,表示最後感冒螞蟻的數目。

樣例輸入

3

5 -2 8

樣例輸出

1

樣例輸入

5

-10 8 -20 12 25

樣例輸出

3

思路

  1. 第一印象就是暴力模拟,用一個數組或者結構體數組模拟螞蟻個體,每一個時鐘改變一次狀态,相遇就取反符号。

    ->這樣做就陷入了出題人的圈套了,這道題本質上是一道智力題,需要仔細觀察,大膽猜測,小心求證。模拟的話,一方面代碼不好寫,另一方面時間複雜度會非常非常大。不可取。

  2. 這道題在《挑戰程式設計程式設計》中有提到過。最關鍵的一點是:把“兩螞蟻相遇後反向”這個條件了解為:“兩螞蟻相遇後不改變方向”。實質上,這個題目需要就算的是“(感冒)螞蟻的數目”,作為數目統計而言,各個螞蟻本質上是一樣的,相遇後方向改不改變都是“一隻螞蟻向左一隻螞蟻向右”。是以兩螞蟻相遇後反向和兩螞蟻相遇後不改變方向在用于數目統計時,效果是一樣的。

具體思路

  1. 對于一隻初始狀态朝右的螞蟻,即數組第一個數為正數時。考慮它的右側有沒有方向相反的螞蟻。為什麼?因為如果右側沒有異向的螞蟻,那麼在“螞蟻每次移動一厘米”的條件下,第一隻感冒螞蟻左側的螞蟻不會接觸到它,右側的隻有同向的也不會接觸到它,是以數目為1。如果右側有異向的螞蟻,那麼這些螞蟻都會被感染,此外,這些異向的螞蟻還會繼續往前行走,與初始螞蟻左側的狀态朝右走的螞蟻相遇。是以,這種情況下,數目為右側異向螞蟻數目+左側同向螞蟻數目。
  2. 對于一隻初始狀态朝左的螞蟻,數目統計就與上述相反。若左側沒有異向的螞蟻,數目為1 。若有,則數目為左側異向螞蟻數目+右側同向螞蟻數目。

代碼

代碼沒儲存…不想敲了(:逃