前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >leetcode (1、2、3)

leetcode (1、2、3)

作者头像
润森
发布2019-11-11 23:39:51
4770
发布2019-11-11 23:39:51
举报
文章被收录于专栏:毛利学Python毛利学Python

在 pycharm 和 IDEA 装leetcode插件, 刷起来贼爽

登录 leetcode 账号:开搞

要求 java 和 py 方法

之前写过,很快就不会了,果然还是要五毒刷题法

五毒刷题法 (极客覃超)

NO.1 leetcode 两数之和

题目描述

给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。

你可以假设每种输入只会对应一个答案。但是,你不能重复利用这个数组中同样的元素。

示例:

代码语言:javascript
复制
给定 nums = [2, 7, 11, 15], target = 9因为 nums[0] + nums[1] = 2 + 7 = 9所以返回 [0, 1]

py 代码解法

列表解法

代码语言:javascript
复制
def twoSum_1( nums, target):    result = []    for i in range (len(nums)):        onenum = nums[i]        twonum = target - onenum        if twonum in nums:            j = nums.index(twonum)            if i != j:                result.append(i)                result.append(j)                return result

字典解法

代码语言:javascript
复制
def twoSum_2(nums,target):    dict={}    for i in range(len(nums)):        m = nums[i]        if target-m in dict:            return [dict[target-m],i]        dict[m] = i

字典推导式

代码语言:javascript
复制
def twosum_3(nums,target):    l = len(nums)    dict = {nums[i]:i for i in range(l)}    print(dict)    for j in range(l):        a = nums[j]        b = target - a        if b in dict and j != dict[b]:            return [j,dict[b]]

Java

  • 一遍 hashmap 解法
代码语言:javascript
复制
class Solution {    public int[] twoSum(int[] nums, int target) {        /*        使用hashmap         */        int[] res = new int[2];        Map<Integer,Integer> map = new HashMap<Integer,Integer>();        for(int i = 0 ; i<nums.length;i++){            int othernums = target - nums[i];            if (map.get(othernums) != null){                res[0] = map.get(othernums);                res[1] = i;            }            map.put(nums[i],i);        }        return res;    }}
  • 两次遍历 hashmap
代码语言:javascript
复制
class Solution {    public int[] twoSum(int[] nums, int target) {        Map<Integer,Integer> map = new HashMap<Integer, Integer>();        for(int i = 0; i<nums.length;i++){            map.put(nums[i],i);        }        for (int i = 0; i<nums.length;i++){            int othernum = target - nums[i];            if(map.containsKey(othernum) && map.get(othernum) != i){                return new int[] {i,map.get(othernum)};            }        }         return null;    }}

给出两个 非空 的链表用来表示两个非负的整数。其中,它们各自的位数是按照 逆序 的方式存储的,并且它们的每个节点只能存储 一位 数字。

如果,我们将这两个数相加起来,则会返回一个新的链表来表示它们的和。

您可以假设除了数字 0 之外,这两个数都不会以 0 开头。

示例:

代码语言:javascript
复制
输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)输出:7 -> 0 -> 8原因:342 + 465 = 807

py 常规操作

代码语言:javascript
复制
class Solution:    def addTwoNumbers(self, l1: ListNode, l2: ListNode) -> ListNode:        # 将链表转化列表        val1, val2 = [l1.val], [l2.val]        while l1.next:            val1.append(l1.next.val)            l1 = l1.next        while l2.next:            val2.append(l2.next.val)            l2 = l2.next        # 反转列表 用join方法拼接数字 切片[::-1]        num_1 = ''.join([str(i) for i in val1[::-1]])        num_2 = ''.join([str(i) for i in val2[::-1]])        sums =  str(num_1 + num_2)[::-1]        # 将sum转化成链表res        # 头节点        res  = head = ListNode(int(sums[0]))        for i in range(1, len(sums)):            # 拼接            head.next = ListNode(int(sums[i]))            head = head.next        return res

优化:不需要将整个数的和求出,只需要每一位对应相加,

思路:

将结果保存在一个新的链表中,使用两个指针,一个指向头节点,用于返回结果,另一个指向当前节点,用于计算并保存结果。遍历两个输入链表,逐位进行相加,若某一个链表遍历到了结尾,则取 0 参与运算。每一位的数字为两个数字对应位以及进位之和除 10 的余数,而该位是否有进位则是这个和除 10 的商。

代码语言:javascript
复制
class Solution:    def addTwoNumbers(self, l1: ListNode, l2: ListNode) -> ListNode:       # 判断0 还是1        res = 0        root = n = ListNode(0)        while l1 or l2 or res:            v1 = v2 = 0            if l1:                v1 = l1.val                l1 = l1.next            if l2:                v2 = l2.val                l2 = l2.next            # divmod() 函数把除数和余数运算结果结合起来,返回一个包含商和余数的元组(a // b, a % b)。            res, val = divmod(v1 + v2 + res, 10)            n.next = ListNode(val)            n = n.next        return root.next

Java

和上面 python 相同的思路

代码语言:javascript
复制
/** * Definition for singly-linked list. * public class ListNode { *     int val; *     ListNode next; *     ListNode(int x) { val = x; } * } */class Solution {    public ListNode addTwoNumbers(ListNode l1, ListNode l2) {        ListNode root = new ListNode(0);        ListNode cur = root;        int res = 0;        // TODO 如果 l1 和l2为空 ,res = 0, pass res = 1 再执行一遍        while (l1 != null||l2 != null|| res !=0){            if (l1 != null) {                res += l1.val;                l1 = l1.next;            }            if (l2 != null) {                res += l2.val;                l2 = l2.next;            }            cur.next = new ListNode(res%10);            res /= 10;            cur = cur.next;        }        return root.next;    }}

NO3、找出其中不含有重复字符的 最长子串 的长度。

给定一个字符串,请你找出其中不含有重复字符的 最长子串 的长度。

示例 1:

输入: "abcabcbb" 输出: 3 解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。 示例 2:

输入: "bbbbb" 输出: 1 解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。 示例 3:

输入: "pwwkew" 输出: 3 解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。 请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。

hashset,哈希表两种解法

推荐 hashmap 时间复杂度 o(n)

py2 种解法

代码语言:javascript
复制
class Solution:    def lengthOfLongestSubstring(self, s: str) -> int:        if s == '':            return 0        #这样必有一个        res = 1        i = 0        for j in range(1, len(s)):            if s[j] not in s[i:j]:                # s[j] 没有重复出现 res 取 j-i+1                res = max(res, j - i + 1 )            else:                # s[j] 竟然重复出现了 如'abcaa'                # s[i:j].index(s[j]) 指当前 i的位置                i += s[i:j].index(s[j]) + 1        return res

使用字典方法

推荐使用字典方法(性能速度高)

代码语言:javascript
复制
class Solution:    def lengthOfLongestSubstring(self, s: str) -> int:        # start子字符串的起始位置        # maxlength 输出最大子序列的长度        start = maxLength = 0        # 记录每次遍历到的字符,key=char,value=index        usedChar = {}        for i in range(len(s)):            # 如果字符存在于字典中,且位置是在起始位置的右边,说明遇到了重复字符            if s[i] in usedChar and start <= usedChar[s[i]]:                # 将起始位置修改为重复字符第一次出现的位置的右邻                start = usedChar[s[i]] + 1            # 字符不存在于字典中            else:                # 有可能start跳到重复字符,所以用max方法                maxLength = max(maxLength, i - start + 1)            # 更新userdChar            usedChar[s[i]] = i        return maxLength
Java 解法

将 py 代码改写成 Java

代码语言:javascript
复制
import java.util.HashMap;//leetcode submit region begin(Prohibit modification and deletion)class Solution {    public int lengthOfLongestSubstring(String s) {        if (s.length() == 0) return 0;        int max = 0;        HashMap<Character, Integer> hashMap = new HashMap<Character, Integer>();        for (int i = 0 ,j = 0; i < s.length(); i++) {            // j是初始位置 重复出现字符            // j将起始位置修改为重复字符第一次出现的位置的右邻            if (hashMap.containsKey(s.charAt(i))) {                j = Math.max(j, hashMap.get(s.charAt(i)) + 1);            }            // 更新hashmap            hashMap.put(s.charAt(i),  i);            max = Math.max(max, i - j + 1);        }        return max;    }}
本文参与?腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2019-11-10,如有侵权请联系?cloudcommunity@tencent.com 删除

本文分享自 小刘IT教程 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与?腾讯云自媒体分享计划? ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • NO.1 leetcode 两数之和
    • 题目描述
      • py 代码解法
        • Java
          • py 常规操作
            • 思路:
          • Java
            • NO3、找出其中不含有重复字符的 最长子串 的长度。
              • py2 种解法
                • Java 解法
            领券
            问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
            http://www.vxiaotou.com