1. 程式人生 > 其它 >LeetCode寒假刷題 Day04

LeetCode寒假刷題 Day04

技術標籤:Leetcodeleetcode連結串列字串資料結構演算法

文章目錄


前言

LeetCode第4天,今天主要用到的是雙指標知識以及一些簡單的棧和連結串列的操作。

一、016 最接近的三數之和

1. 題目描述

題號:16
難度:中等
最接近的三數之和
給定一個包括n個整數的陣列nums和一個目標值target。找出nums中的三個整數,使得它們的和與target最接近。返回這三個數的和。假定每組輸入只存在唯一答案。

示例 :

例如,給定陣列 nums = [-1,2,1,-4], 和 target = 1. 與 target 最接近的三個數的和為 2.
(-1 +2 + 1 = 2).

2. 解題思路

與昨天的 015 三數之和 類似,採用雙指標的思想,避免了暴力的三重迴圈。

3. 程式碼實現

class Solution {
    public int threeSumClosest(int[] nums, int target) {
        Arrays.sort(nums);
        if(nums.length==3)
            return nums[0]+nums[
1]+nums[2]; int i=0,j=1,k=2; int value=Integer.MAX_VALUE; int pre=value; int val=Integer.MAX_VALUE; int flag=1; while(i< nums.length-1) { while(i>=0&&k< nums.length&&val!=0) { value=
nums[i]+nums[j]+nums[k]-target; val=Math.min(val,Math.abs(value)); if(val==-value) flag=-1; else if(val==value) flag=1; pre=value; if(value>0) { if(i==0) --i; while (i > 0 && nums[--i] == nums[i + 1]); } else { if(k==nums.length-1) ++k; while(k< nums.length-1&&nums[++k]==nums[k-1]); } continue; } if(val==0) { return target; } ++j; i=j-1; k=j+1; } return target+flag*val; } }

二、020 有效的括號

1. 題目描述

題號:20
難度:簡單
有效的括號
給定一個只包括 ‘(’,’)’,’{’,’}’,’[’,’]’ 的字串,判斷字串是否有效。

有效字串需滿足:

左括號必須用相同型別的右括號閉合。
左括號必須以正確的順序閉合。
注意空字串可被認為是有效字串。

示例 1:

輸入: “()”
輸出: true
示例 2:

輸入: “()[]{}”
輸出: true
示例 3:

輸入: “(]”
輸出: false
示例 4:

輸入: “([)]”
輸出: false
示例 5:

輸入: “{[]}”
輸出: true
示例 6:

輸入: “”
輸出: true
示例 7:

輸入: “((”
輸出: false

2. 解題思路

這個不用多說了,就是簡單的括號匹配,一般而言,關於表示式求值、括號匹配等問題,都是通過棧來實現。

就這道問題而言,我們可以首先將表示式中的字首括號“( [ { ”入棧,若遇到的不是這三個,則為字尾括號,將出棧並與之匹配;若兩者不匹配,返回false。若此時棧中沒有元素,返回false。若最終表示式遍歷完後,棧仍然不為空,返回false。其餘情況,最終的返回值為true。

3. 程式碼實現

class Solution {
    public boolean isValid(String s) {
        if(s.length()%2==1)
            return false;
        int i=0,j=s.length()-1;
        Map<Character,Character> map =new HashMap<Character,Character>();
        map.put('[',']');
        map.put('{','}');
        map.put('(',')');
        Stack <Character>stack=new <Character>Stack();
        for(i=0;i<s.length();i++)
        {
            if(map.containsKey(s.charAt(i)))
                stack.push(s.charAt(i));
            else
            {
                if(stack.empty())
                    return false;
                if(map.get(stack.pop())!=s.charAt(i))
                    return false;
            }
        }
        if(!stack.empty())
            return false;
        return true;
    }
}

三、021 合併兩個有序連結串列

1. 題目描述

題號:21
難度:簡單
合併兩個有序連結串列
將兩個有序連結串列合併為一個新的有序連結串列並返回。新連結串列是通過拼接給定的兩個連結串列的所有節點組成的。

示例:

輸入:1->2->4, 1->3->4
輸出:1->1->2->3->4->4

2. 解題思路

藉助了歸併排序中的將兩個有序數組合併為一個的思想。為了不new新的節點佔用空間,我們將l1連結串列作為基準連結串列,將l2插入l1的適當位置。

3. 程式碼實現

class Solution {
    public ListNode mergeTwoLists(ListNode l1, ListNode l2) {
        if(l1==null)
            return l2;
        ListNode head1=new ListNode(0,l1);
        l1=head1;
        ListNode head2=new ListNode(0,l2);
        ListNode now=l2;
        while(head1.next!=null&&head2.next!=null)
        {
            if(head2.next.val<head1.next.val)
            {
                now=head2.next;
                head2.next=now.next;
                now.next=head1.next;
                head1.next=now;
                head1=now;

            }
            else
            {
                head1=head1.next;
            }

        }
        while(head2.next!=null)
        {
            now=head2.next;
            head2.next=now.next;
            now.next=head1.next;
            head1.next=now;
            head1=now;
        }
        l1=l1.next;
        return l1;
    }
}

總結

以上就是今天LeetCode寒假刷題的第四天所做的三道題。若有任何疑問,歡迎私信Call我鴨!