[学习笔记-C++篇]day23 剑指24,35,05,58,03

配套力扣剑指offer剑指 Offer
刷题顺序同上。同时结合书上内容。


1. 剑指 Offer 24. 反转链表

牛客做过。注意一下,要考虑到当前节点head为空的可能性,要加一句判断。

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* reverseList(ListNode* head) {
        ListNode* tmp;
        ListNode* nex=nullptr;

        if(head==nullptr || head->next==nullptr) return head;

        while(head->next!=nullptr)
        {
            tmp=head->next;//先保存正序的下一个指针
            head->next=nex;//重新给next赋值
            nex=head;//更新下一次用于赋值给next的内容
            head=tmp;//迭代节点
        }
        head->next=nex;//给最后节点赋next,变成新的头节点
        return head;
    }
};

2. 剑指 Offer 35. 复杂链表的复制

一开始考虑直接返回head,不行。
考虑只拷贝第一个节点,后面节点不变,不行。会检测新的节点是不是原来的节点的拷贝,或者是否指向原来的节点。

只考虑单链表,其实比较简单,除了要先把头节点建立,判断有没有下一节点,没有就给nullptr,有就先构建nex,然后把headcur,构建curnex关系;然后循环判断nex的下一节点是否为空,不为空就先把nexcur,然后找一下下一节点nex,再创建指向;最后再把nex的下一节点给nullptr就可以。

但是复杂链表的话random节点不好直接构建连接,因为有的节点可能还没有构建。

要用哈希。学一下。

作者:jyd
链接:https://leetcode-cn.com/problems/fu-za-lian-biao-de-fu-zhi-lcof/solution/jian-zhi-offer-35-fu-za-lian-biao-de-fu-zhi-ha-xi-/
来源:力扣(LeetCode)

class Solution {
public:
    Node* copyRandomList(Node* head) {
        if(head == nullptr) return nullptr;//先判空,为空直接输出空指针
        Node* cur = head;
        unordered_map<Node*, Node*> map;
        // 3. 复制各节点,并建立 “原节点 -> 新节点” 的 Map 映射
        while(cur != nullptr) {
            map[cur] = new Node(cur->val);//利用map容器实现节点复制,注意这里要用new分配内存,每个原始链表的节点作为key,复制的节点作为value
            cur = cur->next;
        }
        
        cur = head;
        // 4. 构建新链表的 next 和 random 指向
        while(cur != nullptr) {
            map[cur]->next = map[cur->next];//这里非常精彩,原始链表节点作为key相当于索引,去定位复制节点
            map[cur]->random = map[cur->random];
            cur = cur->next;
        }
        // 5. 返回新链表的头节点
        return map[head];
    }
};

3. 剑指 Offer 05. 替换空格

注意stringpush_back()只能增加1个字符。

class Solution {
public:
    string replaceSpace(string s) {
        int size=s.size();
        string ss;
        for(int i=0;i<size;i++)
        {
            if(s[i]!=' ') ss.push_back(s[i]);
            else
            {
                ss.push_back('%');
                ss.push_back('2');
                ss.push_back('0');
            }
        }
        return ss;
    }
};

4. 剑指 Offer 58 - II. 左旋转字符串

主要用到stringassign函数,注意str.assign(s,index,num);,把sindex开始的num个字符赋值给str,然后字符串可以直接相加。

class Solution {
public:
    string reverseLeftWords(string s, int n) {
        string str;
        int k=n%s.size();
        if(k==0) return s;

        str.assign(s,k,s.size()-k);
        string stmp;
        stmp.assign(s,0,k);
        str+=stmp;
        return str;
    }
};

5. 剑指 Offer 03. 数组中重复的数字

看到要统计数字个数,而且统计的数字不重复,就想到应用以下unordered_map,但是其实遍历挺耗时的。

class Solution {
public:
    int findRepeatNumber(vector<int>& nums) {
        unordered_map<int,int> memo;
        for(auto i:nums)//注意这里就是遍历nums的每一个元素
        {
            memo[i]++;//一旦有重复数字就个数+1
        }
        for(int i=0;i<memo.size();i++)
        {
            if(memo[i]>1) return i;
        }
        return 0;
    }
};
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值