python(剑指offer25-28题)

25.输入一个复杂链表(每个节点中有节点值,以及两个指针,一个指向下一个节点,另一个特殊指针指向任意一个节点),返回结果为复制后复杂链表的head。(注意,输出结果中请不要返回参数中的节点引用,否则判题程序会直接返回空)

方法一:也算是最普遍的算法,分两次复制;

class Solution:
    # 返回 RandomListNode
    def Clone(self, pHead):
        # write code here
        # 复制原链表,组合成新链表
        if not pHead:
            return None
        cloNode = pHead
        while cloNode:
            # 创建新节点
            node = RandomListNode(cloNode.label)
            node.next = cloNode.next
            # 将新节点赋值给cloNode的下一个节点,等到拆分时,第一次赋值的节点相当于头
            cloNode.next = node
            # 将头节点指向原链表的下一项
            cloNode = node.next
        # 将指针从新指向头,为复制随机指针作准备
        cloNode = pHead
        # 复制原链表中的随机指针
        while cloNode:
            node = cloNode.next
            # 若是有随机指针就进行复制
            if cloNode.random:
                node.random = cloNode.random.next
            # 向后移动1位,此时相当于移动了2位
            cloNode = node.next
        cloNode = pHead
        pHead = cloNode.next
        # 拆分链表
        while cloNode:
            node = cloNode.next
            cloNode = node.next
            if cloNode is None:
                break
            node.next = cloNode.next
        # 返回头,此时头已经指向第二个了
        return pHead

方法二:递归

 def Clone(self, pHead):
        # write code here
        if not pHead: return
        newNode = RandomListNode(pHead.label)
        newNode.random = pHead.random
        newNode.next = self.Clone(pHead.next)
        return newNode

方法三:深度复制

26输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的双向链表。要求不能创建任何新的结点,只能调整树中结点指针的指向。

class Solution:
    def Convert(self, pRootOfTree):
        # write code here
        if pRootOfTree is None:
            return None
        self.linklast = None # 用于保存递归中最后一个节点
        self.conver(pRootOfTree)
        phead = self.linklast
        # 循环进行左连接
        while phead and phead.left:
            phead = phead.left
        return phead
    # 递归中序遍历二叉搜索树
    def conver_node(self, root):
        if not root:return 
        pcurr = root # 保存当前节点
        if pcurr.left:
            self.conver(pcurr.left)
        pcurr.left = self.linklast
        # 将上个节点right指向下个中序遍历的节点
        if self.linklast:
            self.linklast.right = pcurr
        # 同步指向的节点,相当于指向最新的中序结果
        self.linklast = pcurr
        if pcurr.right:
            self.conver(pcurr.right)

27.输入一个字符串,按字典序打印出该字符串中字符的所有排列。例如输入字符串abc,则打印出由字符a,b,c所能排列出来的所有字符串abc,acb,bac,bca,cab和cba。通过递归实现多重for循环,参考自牛客网杨少

class Solution:
    def Permutation(self, ss):
        # write code here
        # ''并不等于空
        if len(ss) <= 0:
            return []
        # 用于存取组合结果
        res = list()
        self.perm(ss, res, '')
        # 通过set()进行去重
        res = list(set(res))
        # 通过sorted进行排序
        return sorted(res)
    
    def perm(self, ss, res, path):
        # 递归结束条件,当ss为‘’,时说明path已经组合完了
        if ss == '':
            # 将递归结果添加到path中
            res.append(path)
        else:
            # 对ss进行循环,每次递归ss长度都减少1
            for i in range(len(ss)):
                # ss[:i]+ss[i+1:] 相当于是从ss中选择第i个添加到path中
                self.perm(ss[:i] + ss[i+1:], res, path + ss[i])

28.数组中有一个数字出现的次数超过数组长度的一半,请找出这个数字。例如输入一个长度为9的数组{1,2,3,2,2,2,5,4,2}。由于数字2在数组中出现了5次,超过数组长度的一半,因此输出2。如果不存在则输出0。

通过第一次循环统计每个数出现的次数,第二次循环找出出现次数大于数组长度一半的值。

class Solution:
    def MoreThanHalfNum_Solution(self, numbers):
        # write code here
        dic = dict()
        # 统计每个数出现的次数 
        for i in numbers:
            if i not in dic:
                dic[i] = 0
            dic[i] = dic[i]+1
        length = len(numbers) // 2
        # 找出出现次数大于一半的数
        for i in dic:
            if dic[i] > length:
                return i
        else:
            return 0

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值