C# 算法題系列(一) 兩數之和、無重復字符的最長子串


題目一

原題鏈接 https://leetcode-cn.com/problems/two-sum/

給定一個整數數組 nums 和一個目標值 target,請你在該數組中找出和為目標值的那 兩個 整數,並返回他們的數組下標。

你可以假設每種輸入只會對應一個答案。但是,你不能重復利用這個數組中同樣的元素。

示例:

給定 nums = [2, 7, 11, 15], target = 9

因為 nums[0] + nums[1] = 2 + 7 = 9
所以返回 [0, 1]

提示:不能自身相加。

測試用例

[2,7,11,15]
9
預期結果
[0,1]

格式模板

public class Solution {
    public int[] TwoSum(int[] nums, int target) {
    /*
    代碼
    */
        }
    }

 

筆者的代碼,僅供參考

使用暴力方法,運行時間 700ms-1100ms

public class Solution {
    public int[] TwoSum(int[] nums, int target) {
         int [] a = new int[2];
            for (int i = 0; i < nums.Length - 1; i++)
            {
                for (int j = i + 1; j < nums.Length; j++)
                {
                    if (nums[i] + nums[j] == target)
                    {
                        a[0] = i;
                        a[1] = j;
                    }
                }
            }
            return a;
        }
    }

運行時間 400ms-600ms

由於使用的是哈希表,所以缺點是鍵不能相同。

public class Solution {
    public int[] TwoSum(int[] nums, int target) {
                     int[] a = new int[2];
            System.Collections.Hashtable hashtable = new System.Collections.Hashtable();
            for(int i = 0; i < nums.Length; i++)
            {
                hashtable.Add(nums[i], i);
            }
            for(int i = 0; i < nums.Length; i++)
            {
                int complement = target - nums[i];
                if (hashtable.ContainsKey(complement) && int.Parse(hashtable[complement].ToString())!=i)
                {
                    a[0] = i;
                    a[1] = int.Parse(hashtable[complement].ToString());
                }
            }
            return a;
        }
    }

 還是哈希表,缺點是哈希表存儲的類型是object,獲取值時需要進行轉換。

        public int[] TwoSum(int[] nums, int target)
        {
            int[] a = new int[2];
            System.Collections.Hashtable h = new System.Collections.Hashtable();
            for (int i = 0; i < nums.Length; i++)
            {
                int c = target - nums[i];
                if (h.ContainsKey(c))
                {
                    a[0] = int.Parse(h[c].ToString()) <= nums[i] ? int.Parse(h[c].ToString()) : i;
                    a[1] = int.Parse(h[c].ToString()) > nums[i] ? int.Parse(h[c].ToString()) : i;
                }
                else if (!h.ContainsKey(nums[i]))
                {
                    h.Add(nums[i], i);
                }
            }
            return a;
        }

抄一下別人的

public class Solution
{
    public int[] TwoSum(int[] nums, int target)
    {
        int[] res = {0, 0};
        int len = nums.Length;
        Dictionary<int, int> dict = new Dictionary<int, int>();
        for (int i = 0; i < len; i++)
        {
            int query = target - nums[i];
            if (dict.ContainsKey(query))
            {
                int min = (i <= dict[query]) ? i : dict[query];
                int max = (i <= dict[query]) ? dict[query] : i;
                return new int[] { min, max };
            }
            else if (!dict.ContainsKey(nums[i]))
            {
                dict.Add(nums[i], i);
            }
        }

        return res;
    }
}
--------------------- 
作者:Bruce-Yeung 
來源:CSDN 
原文:https://blog.csdn.net/lzuacm/article/details/80551669 
版權聲明:本文為博主原創文章,轉載請附上博文鏈接!

 

題目二

原題地址 https://leetcode-cn.com/problems/longest-substring-without-repeating-characters/

給定一個字符串,請你找出其中不含有重復字符的 最長子串 的長度。

示例 1:

輸入: "abcabcbb"
輸出: 3 
解釋: 因為無重復字符的最長子串是 "abc",所以其長度為 3

示例 2:

輸入: "bbbbb"
輸出: 1
解釋: 因為無重復字符的最長子串是 "b",所以其長度為 1

示例 3:

輸入: "pwwkew"
輸出: 3
解釋: 因為無重復字符的最長子串是 "wke",所以其長度為 3

要注意字符串為空、變量為null、字符串長度 Length = 1 等情況。

測試實例

輸入
" "
"au"
"abcabcbb"
"bbbbb"
"pwwkew"
"aab"

預期結果分別是 1,2,3,1,3,2

代碼格式模板

public class Solution {
    public int LengthOfLongestSubstring(string s) {
        
    }
}

 

筆者的代碼僅供參考

使用最笨的方式,200ms左右

public class Solution {
    public int LengthOfLongestSubstring(string s) {
                    if (s == null || s == "")
                return 0;

            char[] a = s.ToCharArray();      //字符串轉為字符數組
            int start = 0;                   //區間開始位置
            int stop = 0;                    //區間結束位置
            int newMax = 1;                   //當前區間數
            int max = 1;                     //區間最大個數

            for (stop = 1; stop < a.Length; stop++)   //每次向后移動一位
            {
                bool b = false;                       //是否存在重復
                for (int i = start; i < stop; i++)  //檢查當前元素在區間是否有相同值
                {
                    if (a[stop] == a[i])        //如果stop+1位在區間找到相同的字符
                    {
                        char ls = a[stop];
                        if (newMax > max) max = newMax;
                        start = i + 1;              //區間開始位置重置
                        newMax = stop - start + 1;
                        b = true;            
                        break;
                    }
                }
                if (b == false)
                    newMax += 1;
            }
            if (newMax > max) max = newMax;
            return max;
    }
}

完整測試代碼(控制台)

using System;

namespace ConsoleApp1
{
    public class Testa
    {
        public int LengthOfLongestSubstring(string s)
        {
            if (s == null || s == "")
                return 0;

            char[] a = s.ToCharArray();      //字符串轉為字符數組
            int start = 0;                   //區間開始位置
            int stop = 0;                    //區間結束位置
            int newMax = 1;                   //當前區間數
            int max = 1;                     //區間最大個數

            for (stop = 1; stop < a.Length; stop++)   //每次向后移動一位
            {
                bool b = false;                       //是否存在重復
                for (int i = start; i < stop; i++)  //檢查當前元素在區間是否有相同值
                {
                    if (a[stop] == a[i])        //如果stop+1位在區間找到相同的字符
                    {
                        char ls = a[stop];
                        if (newMax > max) max = newMax;
                        start = i + 1;              //區間開始位置重置
                        newMax = stop - start + 1;      //重新設置區間數
                        b = true;            
                        break;
                    }
                }
                if (b == false)             ////沒有重新設置區間數時加1
                    newMax += 1;
            }
            if (newMax > max) max = newMax;
            return max;
        }
    }
    class Program
    {


        static void Main(string[] args)
        {
            Testa t1 = new Testa();                                     //正確結果
            Console.WriteLine(t1.LengthOfLongestSubstring(" "));        //1
            Console.WriteLine(t1.LengthOfLongestSubstring("au"));       //2
            Console.WriteLine(t1.LengthOfLongestSubstring("abcabcbb")); //3
            Console.WriteLine(t1.LengthOfLongestSubstring("bbbbb"));    //1
            Console.WriteLine(t1.LengthOfLongestSubstring("pwwkew"));   //3
            Console.WriteLine(t1.LengthOfLongestSubstring("aab"));      //2
            Console.ReadKey();
        }
    }
}

 

使用哈希集合,速度更快,100ms-150ms

        public int LengthOfLongestSubstring(string s)
        {
            int n = s.Length;
            HashSet<char> set = new HashSet<char>();        //集合
            int ans = 0, start = 0, stop = 0;               //ans為字符串長度,starp區間起點,stop區間終點
            while (start < n && stop < n)
            {
                // try to extend the range [i, j]
                if (!set.Contains(s[stop]))
                {
                    set.Add(s[stop++]);
                    ans = Math.Max(ans, stop - start);
                    //或者ans = ans > (stop - start) ? ans : (stop - start)
                }
                else
                {
                    set.Remove(s[start++]);
                }
            }
            return ans;
        }

 

完整控制台測試代碼

using System;
using System.Collections.Generic;
using System.Linq;

namespace ConsoleApp2
{
    public class Solution
    {
        public int LengthOfLongestSubstring(string s)
        {
            int n = s.Length;
            HashSet<char> set = new HashSet<char>();        //集合
            int ans = 0, start = 0, stop = 0;               //ans為字符串長度,starp區間起點,stop區間終點
            while (start < n && stop < n)
            {
                // try to extend the range [i, j]
                if (!set.Contains(s[stop]))
                {
                    set.Add(s[stop++]);
                    ans = Math.Max(ans, stop - start);
                    //或者ans = ans > (stop - start) ? ans : (stop - start)
                }
                else
                {
                    set.Remove(s[start++]);
                }
            }
            return ans;
        }
    }
    class Program
    {
        static void Main(string[] args)
        {

            Solution t1 = new Solution();                                     //正確結果
            Console.WriteLine(t1.LengthOfLongestSubstring(" "));        //1
            Console.WriteLine(t1.LengthOfLongestSubstring("au"));       //2
            Console.WriteLine(t1.LengthOfLongestSubstring("abcabcbb")); //3
            Console.WriteLine(t1.LengthOfLongestSubstring("bbbbb"));    //1
            Console.WriteLine(t1.LengthOfLongestSubstring("pwwkew"));   //3
            Console.WriteLine(t1.LengthOfLongestSubstring("aab"));      //2
            Console.ReadKey();
        }
    }
}

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM