C++面试篇

要求:
各种常用的排序算法:冒泡、快排、插入、堆排序、希尔、基数或桶排序
查找算法:二分查找、插值查找、顺序查找
数据结构:链表、树、堆、栈、顺序表
各种字符串函数如strlen,strcpy,strcat,strstr,strcmp,strchr
智能指针share_ptr,weak_ptr,unique_ptr
经典算法类:经典算法如动态规划、回溯法、贪婪算法、图的遍历算法。
经典题目:剑指offer、leedcode上的题比如反转链表等题目。


list基础:代码如下:

void listTest()
    {
        list<int> l1;
        list<int> l2(2, 0);
        list<int>::iterator iter;

        l1.push_back(1);
        l1.push_back(2);
        l2.push_back(2);
        l1.merge(l2, greater<int>());
        iter = l1.begin();

        while (iter != l1.end())
        {
            cout << *iter++ << " ";
        }

        cout << "" << endl;

        l1.sort();
        l1.reverse();
        iter = l1.begin();

        while (iter != l1.end())
        {
            cout << *iter++ << " ";
        }

        cout << "" << endl;
        l1.push_front(99);
        l1.push_back(100);
        iter = l1.begin();
        advance(iter, 3);
        l1.insert(iter, 666);

        iter = l1.begin();

        while (iter != l1.end())
        {
            cout << *iter++ << " ";
        }
    }

queue 基础:
缺点:O(n)时间复杂度,入队和出队都要整体移动内存
重点:如何实现------------循环队列
像是一根管子,先进先出
循环队列实现:模板类+数组(构造参数是容量的大小)

    void queueTest()
    {
        queue<int> q;

        for (int i = 0; i < 10; i++)
        {
            //队尾push数据
            q.push(i);
        }

        cout << "q中有: " << q.size() << endl;
        cout << "队首数据:" << q.front() << endl;
        cout << "队尾数据:" << q.back() << endl;
        q.pop();
        cout << "队首数据:" << q.front() << endl;
    }

vector基础:  
如何进行vector内存置0:

vec.clear();

如何进行vector内存回收:vector<int>().swap();

vector<int>().swap(vec);

使用vector定义二维数组:

    vector<vector<int> > A;//正确的定义方式
    printf("%d\n", A[0][1]);

reserve和resize有什么区别?

 resize会填0操作,reserve不会。都会改vec.capacity()

以下是vector简单练习测试:

void vectorTest()
    {
        vector<int> vec = {1, 2, 3, 88};
        vector<int>::iterator iter;
        iter = find(vec.begin(), vec.end(), 48);

        if (iter != vec.end())
        {
            cout << "find it: " << *iter << endl;
            //删除某个元素
            vec.erase(iter);
            iter = vec.begin();

            while (iter != vec.end())
            {
                cout << *iter++ << " ";
            }
        }
        else
            cout << "can not find it! " << endl;

        //插入元素99
        iter = vec.begin();
        advance(iter, 3);
        vec.insert(iter, 99);

        iter = vec.begin();
        cout << endl;

        while (iter != vec.end())
        {
            cout << *iter++ << " ";
        }

        cout << endl;

        vec.clear();
        vector<int>().swap(vec);

        if (!vec.empty())
            vec.pop_back();
        else
            cout << "vec empty" << endl;

        cout << vec.size() << " " << vec.capacity();
    }

锁的一些概念:
要使用悲观锁,必须关闭 MySQL 数据库的自动提交属性set autocommit=0。
因为 MySQL 默认使用 autocommit 模式,也就是说,当执行一个更新操作后,
MySQL 会立刻将结果进行提交。

常用互斥锁和自旋锁的区别是:

自旋锁不会让出CPU资源。

互斥锁会让出CPU资源,进而导致线程切换。


脏写、脏读、不可重复读、幻读的概念

脏写:
    而它的本质就是事务 B 去修改了事务 A 修改过的值,
    但是此时事务 A 还没提交,所以事务 A 随时会回滚,
    导致事务 B 修改的值也没了,这就是脏写的定义
脏读:
    它的本质是事务 B 去查询了事务 A 修改过的数据,
    但是此时事务 A 还没提交,所以事务 A 随时会回滚导致事务 
    B 再次查询就读不到刚才事务 A 修改的数据了,这就是脏读
不可重复读:
    让你事务 A 执行期间多次查到的值都不一样,
    都的问题是别的提交过的事务修改过的,
    那么此时你就可以认为,数据库有问题,
    这个问题就是「不可重复读」
幻读:
    幻读就是你一个事务用一样的 SQL 多次查询,
    结果每次查询都会发现查到一些之前没看到过的数据。
    注意,幻读特指的是你查询到了之前查询没看到过的数据

redis相关的知识:
1.redis 网络
2.redis pipeline
3.redis 事务
4.redis pub/sub lua脚本
5.异步连接实现

1.redis 网络
单线程:单线程reactor   网络io  (mysql还有磁盘io)
把活跃连接进行--

每条连接-----一个对列  (协议包)
reactor-------一个处理器  并发处理

2.redis pipeline
redis pipeline 是一个客户端提供
异步请求,可以多次发送,节约一半时间

lua脚本相关:

采用lua相当于pipeline的效果,具备原子性,单线程执行
优点:
1.减少网络传输
2.原子性

1.script load xx.lua
2.redis-server-------sha1----40位字符串   sha1--->xx.lua映射
例如:
    local script = [[
        local args = KEYS[1]
        
    ]]
    res,err = rds:script("load",script)  //生成hash
    res,err = rds:evalsha(res,1,"mark");
测试的时候:    
    eval script numkeys key [key...]arg[arg...]
热更新lua
    redis-cli script flush   //清除映射lua对
杀死lua脚本:
    script kill 

ACID特性分析:
    1.原子性(全部成功或者全部失败)不具备传统原子性,lua可以实现
    2.一致性  (不具备约束一致性)
    3.隔离性(符合)mysql(MVCC实现)
    4.持久性 aof  fork进程

redis发布订阅   (消息不可达)
    分布式消息
    例如:
    1.subscribe news
    publish news mark
    2.psubscribe news.*
    publish news.showbiz 'jjjjj'

3.redis 事务
key-value
如何实现:
    redis               mysql
    multi------->  begin
    exec-------->  commit
    discard----->  rollback
    watch------->检测key是否变化,有变化就取消事务(乐观锁实现cas)

1.watch key
2.mutil 
3.set key mark
4.exec

实际工作不用,一般采用lua脚本实现事务的原子性
应用:事务来实现zpop
    WATCH zset
    element = ZRANGE zset 0 0
    MUTIL
    ZREM zset element
    EXEC

4.redis pub/sub
5.异步连接实现
    1.单reactor
    2.多reactor,一个reactor专门负责listen  8*reactor负责操作()
    3.协程消除回调 go理解更深刻
    4.协议实现  redis  monogo 

排序算法:

冒泡排序,时间复杂度O(n*2)

内层循环,把最大的数放最后面,所以j总是从0开始,外层一共需要进行size()-1次排序

    int arr[] = { 4, 2, 8, 0, 5, 7, 1, 3, 9 };
	int end = sizeof(arr) / sizeof(arr[0]) - 1;
	for (int i = 0; i < end; i++)
	{
		for (int j = 0; j < end - i; j++)
		{
			if (arr[j] > arr[j + 1])
			{
				int temp = arr[j];
				arr[j] = arr[j + 1];
				arr[j + 1] = temp;
			}
		}


 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值