一道小学题目
偶爾看到的,題目大致如下:
有一個數,abcdefghi,每個字母分別代表了1到9之間的數字(數字不重復),而且該數有一個特性,a能被1整除,ab能被2整除,...abcdefghi能被9整除,求該數。
反正我是不知道小學方法該怎么求,看到這題目,第一反應就是,循環一下就好了——確實最簡單的方法,不過要寫的循環太多,也容易出錯。
再一分析,這不是個遞歸的過程么,即該數能被本身長度所整除。試了一下,果然出結果了。
代碼如下,為了寫起來方便,加了兩個擴展方法。
namespace ConsoleApplication1 {static class Program{static int total = 0;//看看遞歸了多少次const int LENGTH_OF_NUMBER = 9;static void Main(string[] args){string[] list = new string[] { "1", "2", "3", "4", "5", "6", "7", "8", "9" };Console.WriteLine("結果是:{0},共運算:{1}次",GetNumber("",list),total);Console.ReadKey();}/// <summary>/// 遞歸取得正確的數/// </summary>/// <param name="str">當前的字符串</param>/// <param name="list">剩余可用的字符列表</param>/// <returns>錯誤返回空字符串,無錯但是可以繼續,則返回下一個字符,成功則返回結果</returns>static string GetNumber(string str, IEnumerable<string> list){total++;if (str.Length > 0){//如果當前條件都不滿足,后續的就沒必要繼續了if (!str.CanDivBy(str.Length))return "";else if (str.Length == LENGTH_OF_NUMBER) //得到符合的數了,也就沒必要繼續了return str;}foreach (var v in list){string tmp = GetNumber(str + v, list.NewList(v));if (tmp.Length != LENGTH_OF_NUMBER)continue;else{return tmp;}}return "";}/// <summary>/// 是否能被某個整數整除/// </summary>/// <param name="val_str"></param>/// <param name="div"></param>/// <returns>是否可以被整除</returns>public static bool CanDivBy(this string val_str, int div){long val;if (!long.TryParse(val_str, out val))return false;return (val * 1.0 / div - val / div) == 0;}/// <summary>/// 根據當前列表,生成一個不包含指定數的新列表/// </summary>/// <param name="old_list"></param>/// <param name="val"></param>/// <returns></returns>public static IEnumerable<string> NewList(this IEnumerable<string> old_list, string val){int v = int.Parse(val);return from a in old_list where int.Parse(a) != v select a;}} }
結果是:381654729,共運算:523次
比我想像的次數少一些。
請無視代碼中混亂的命名,純粹一時興起驗證一下。
題目還可以改一下,即可以加上0,變成abcdefghij可以被10整除,只要把長度改成10,數組里加個0就好了
轉載于:https://www.cnblogs.com/varlxj/p/3214401.html
總結
 
                            
                        - 上一篇: wordpress 安装(亲身经历) 出
- 下一篇: Android amr语音编解码解惑 【
