leetcode

动态规划

https://github.com/xuelangZF/LeetCode/tree/master/DynamicProgramming

分而治之

https://github.com/xuelangZF/LeetCode/tree/master/DivideConquer

贪心算法

https://github.com/xuelangZF/LeetCode/tree/master/Greedy

深度优先

https://github.com/xuelangZF/LeetCode/tree/master/DepthFirstSearch

广度优先

https://github.com/xuelangZF/LeetCode/tree/master/BreadthFirstSearch

二分搜索

https://github.com/xuelangZF/LeetCode/tree/master/BinarySearch

回溯

https://github.com/xuelangZF/LeetCode/tree/master/Backtracking

数学知识

https://github.com/xuelangZF/LeetCode/tree/master/Math

位运算的技巧

https://github.com/xuelangZF/LeetCode/tree/master/BitManipulation

高频前100个:https://leetcode.com/problemset/top-100-liked-questions/

面试高频类:https://leetcode.com/problemset/top-interview-questions/

字节跳动(头条)常考题:https://leetcode-cn.com/explore/interview/card/bytedance/

腾讯2018秋招常考题:https://leetcode-cn.com/problemset/2018-50/
2. Add Two Numbers

You are given two non-empty linked lists representing two non-negative integers. The digits are stored in reverse order and each of their nodes contain a single digit. Add the two numbers and return it as a linked list.

You may assume the two numbers do not contain any leading zero, except the number 0 itself.

Example:

Input: (2 -> 4 -> 3) + (5 -> 6 -> 4)
Output: 7 -> 0 -> 8
Explanation: 342 + 465 = 807.
class ListNode:
    def __init__(self, x):
        self.val = x
        self.next = None

class Solution:
    # @return a ListNode
    # def addTwoNumbers1(self, l1, l2):
    #     if l1 is None:
    #         return l2
    #     elif l2 is None:
    #         return l1
    #     else:
    #         carry = 0
    #         #插入头节点
    #         ret = ListNode(0)
    #         ret_Last = ret
    #         while l1 or l2:
    #             sum = 0
    #             if l1:
    #                 sum = l1.val
    #                 l1 = l1.next
    #             if l2:
    #                 sum += l2.val
    #                 l2 = l2.next
    #             sum += carry
    #             #如果有进 位时的处理方式
    #             ret_Last.next = ListNode(sum % 10)
    #             ret_Last = ret_Last.next
    #             carry = (sum >= 10) #进位的值为1

    #         if (carry):
    #             ret_Last.next = ListNode(1) #将进位传给next
    #         ret_Last = ret.next
    #         del ret
    #         return ret_Last

    def addTwoNumbers(self, l1, l2):
        """
        :type l1: ListNode
        :type l2: ListNode
        :rtype: ListNode
        """
        if l1 is None:
            return l2
        elif l2 is None:
            return l1
        else:
            #进位为0
            carry = 0
            add = ListNode(0)
            add_last = add
            while l1 or l2:
                val_sum = 0
                if l1:
                    val_sum = l1.val
                    l1 = l1.next
                if l2:
                    val_sum +=l2.val
                    l2 = l2.next
                val_sum += carry
                add_last.next = ListNode(val_sum%10)
                add_last = add_last.next
                #判断是否有进位
                carry = (val_sum>=10)

            if carry:
                add_last = ListNode(1)
            add_last = add.next
            del add
            return add_last

if __name__ == '__main__':
#建立链表
#l1列表
    l1_1 = ListNode(2)
    l1_2 = ListNode(4)
    l1_3 = ListNode(3)
    l1_1.next = l1_2
    l1_2.next = l1_3
#l2列表
    l2_1 = ListNode(8)
    l2_2 = ListNode(6)
    l2_3 = ListNode(9)
    l2_1.next = l2_2
    l2_2.next = l2_3
#l3列表存放的是两个列表中的数的和
l3_1 = Solution().addTwoNumbers(l1_1,l2_1)

while l3_1 != None:
    print(l3_1.val)
    l3_1 = l3_1.next

最长回文子串的动态规划的解法以及暴力解法和中心扩展法:

动态规划:

子问题:

  以i开始,以j结束的子串的最长回文串

状态:

      令P[i,j]表示:以i开始,以j结束的子串是否为回文串。其值为0,1。P[i,j]==0表示子串s[i:j]不是回文串,P[i,j]==1表示子串s[i:j]是回文串。

状态转移方程:

   

例子

https://blog.csdn.net/u012613903/article/details/79146533

在动态规划的思想中,总是希望把问题划分成相关联的子问题;然后从最基本的子问题出发来推导较大的子问题,直到所有的子问题都解决。

首先要看一个较大的子问题与一个较小的子问题之间的关系:

首先建立如下的函数:

那么就能有如下的递推关系:

当p(i+1,j-1)  = true 的时候,如果有si == sj,那么 p(i,j)=true;也就是 abba中的bb为回文串,那么在bb左边是a,在bb右边也是a,相同;所以有abba也是回文串。

形式化表示如下: p(i,j) = p(i+1,j-1) and si==sj    这就建立了较大问题与较小问题之间的关系。

然后考虑基本情况,一个最基本的回文串有两种情况(奇偶性):

(1) 最基本的奇回文,只有一个字符,而且恒成立;形式化表示为 p(i,i) = true

(2)最基本的偶回文,有两个字符,当且仅当两个字符相等的时候成立p(i,j) = (si==sj and j=i+1)

最后获得如下判断一个字符是否为回文串的分段函数:

在动态规划中,最最最核心的就是填表了,就以程序中的例子"babad"举例,说明一下填表的过程;

首先我们要填的表是如下的一张表二维表(因为p函数中有i,j两个变量),其中绿色的部分是真实的表格,其他的是解释表头。

填表过程如下:首先填长度为1的;

然后填长度为2的

 接着是长度为3的:

长度为4的:

最后是长度为5的:

        length = len(s)
        max_len = 1
        memo = [[-1] * len(s) for i in range(len(s))]
        print(memo)
        #开始填表
        for p_len in range(1,length+1): #考虑长度分别为1,2,3,4,5等
            for i in range(length):
                j = p_len+i-1
                #对应四种不同的情况
                if j<length:
                    if i==j:  #对角线的元素
                        memo[i][j] = 1
                    elif j==i+1 and s[i]==s[j]: #相邻的元素
                        memo[i][j] = 1
                        max_len = p_len
                    elif j>i+1 and memo[i+1][j-1]==1 and s[i]==s[j]: #奇数个数的回文
                        memo[i][j] = 1
                        max_len = p_len
                    else: #最后的其他情况
                        memo[i][j] = 0
        print(memo)
        #打印出所有的子序列
        for i in range(length):
            for j in range(length):
                if memo[i][j]==1 and j-i+1==max_len:
                    print(s[i:j+1])

动态规划之最长公共子序列

https://www.cnblogs.com/zfyouxi/p/4195215.html

https://blog.csdn.net/hrn1216/article/details/51534607

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值