校招刷题笔记

1. 单词倒排

import sys
import re

#r = re.compile("[\W+]")

for line in sys.stdin:
    #print (type(line))
    #print (line)
    list_1 = re.split(r"[^A-Za-z]",line.strip())
    if (len(list_1) ==1):
        list_1 = line.strip().split(" ")
    print(' '.join(list_1[::-1]))
    #print(a)
    # print(int(a[0]) + int(a[1]))

把非字母的部分用空格替代,再以空格为分隔符分割整个字符串,最后将分割后的字符串颠倒。

while True:
    try:
        a=input().strip()
        for i in range(len(a)):
            if not a[i].isalpha():
                a=a.replace(a[i], ' ')
        b=a.split(' ')
        b.reverse()
        print(' '.join(b))
    except:
        break

十大经典排序:https://www.cnblogs.com/onepixel/articles/7674659.html

Python之re模块:https://www.cnblogs.com/shenjianping/p/11647473.html

python中的input().strip().split():
https://blog.csdn.net/qq_41500249/article/details/103130219

2. 进制转换

'''
python将16进制转为10进制可以用int('hex型',16) 八进制转十进制int('八进制型',8) 八进制或十六进制或10进制装二进制直接调用 bin(任意进制) 
'''
while True:
    try:
        s=input()
        print(int(s,16))
    except:
        break
python, try 的用法:

异常即是一个事件,该事件会在程序执行过程中发生,影响了程序的正常执行。捕捉异常可以使用try/except语句。
try/except语句用来检测try语句块中的错误,从而让except语句捕获异常信息并处理。try 的工作原理是,当开始一个try语句后,python就在当前程序的上下文中作标记,这样当异常出现时就可以回到这里,try子句先执行,接下来会发生什么依赖于执行时是否出现异常。
https://www.runoob.com/python/python-exceptions.html

#include<iostream>
#include<string>
using namespace std;

int main(){
    string str;
    while(cin>>str){
        cout << stoi(str,0,16) << endl;
    }
}

stoi 接受 string, 从第一个非空格的字符开始处理(第二个参数为0),以16进制形式输入,转化为十进制输出。

C++ stoi

https://www.cnblogs.com/weedboy/p/7160152.html

找到 ‘x’ (标志着数值开端)所在位置并从该位置开始进制转换,利用ASCII码对每一位逐一转换。

#include<iostream>
using namespace std;
int main(){
    string a;
    while(getline(cin,a)){
        int res=0;
        int pos=a.find('x');
        for(int i=pos+1;i<a.size();++i){
            int tmp=0;
            if(a[i]>='A'&&a[i]<='F'){
                tmp=10+(a[i]-'A');
            }
            else{
                tmp=a[i]-'0';
            }
            res=res*16+tmp;
        }
        cout<<res<<endl;
    }
    return 0;
}
C++ getline

https://www.cnblogs.com/wkfvawl/p/11040760.html

C++ string类

http://c.biancheng.net/view/400.html

3. 字符串排序

while True:
    try:
        num=int(input())
        stack=[]
        for i in range(num):
            stack.append(input())
        print("\n".join(sorted(stack)))        
    except:
        break
Python input() 函数

Python3.x 中 input() 函数接受一个标准输入数据,返回为 string 类型。

https://www.runoob.com/python/python-func-input.html

python sorted() 函数

https://www.runoob.com/python3/python3-func-sorted.html

4. 简单密码

暴力解法,性能不太行但是一目了然 (hhhh…)

while True:
    try:
        s = input()
        res = []
        for i in s:
            if i.isdigit():
                res.append(i)
            elif i.isupper() and i != 'Z':
                res.append(chr(ord(i.lower()) + 1))
            elif i == 'Z':
                res.append('a')
            else:
                if i in 'abc':
                    res.append('2')
                elif i in 'def':
                    res.append('3')
                elif i in 'ghi':
                    res.append('4')
                elif i in 'jkl':
                    res.append('5')
                elif i in 'mno':
                    res.append('6')
                elif i in 'pqrs':
                    res.append('7')
                elif i in 'tuv':
                    res.append('8')
                else:
                    res.append('9')
        print(''.join(res))
    except:
        break


5. 坐标移动

考虑边界情况:
题目中提到了合法坐标是不超过两位数的位移。那就意味着其实可能会有一位数(合法),甚至超过两位数(非法)。如果仅仅只是使用try,except去判断是否能够将第二位之后的int化可能会触发边缘情况。例如输入为A100,那么这个也会是一个有效输入,但是这个并不是合法的坐标位移。

dict.keys()函数也可以作为判断机制。

input_list = input().split(';')
initial = [0,0]

for item in input_list:
    if not 2 <= len(item) <= 3:
        continue

    try:
        direction = item[0]
        step = int(item[1:])
        if direction in ['A', 'D', 'W', 'S']:
            if 0 <= step <= 99:
                if direction == 'A':
                    initial[0] -= step
                elif direction == 'D':
                    initial[0] += step
                elif direction == 'S':
                    initial[1] -= step
                elif direction == 'W':
                    initial[1] += step
    except:
        continue

print(str(initial[0]) + ',' + str(initial[1]))

6. 动态规划

知识点总结:
http://blog.csdn.net/misayaaaaa/article/details/71794620

经典走阶梯问题:
https://www.cnblogs.com/liuyicai/p/10182262.html
多种解法:
https://blog.csdn.net/misayaaaaa/article/details/71940779

以及其他典型问题:
https://blog.csdn.net/weixin_42182348/article/details/90814032

扩展:
https://zhuanlan.zhihu.com/p/348271753

算法框架:
https://www.cnblogs.com/forcheryl/p/3987203.html

阶梯问题
解法一:
分析:
假定n=10,首先考虑最后一步的情况,要么从第九级台阶再走一级到第十级,要么从第八级台阶走两级到第十级,因而,要想到达第十级台阶,最后一步一定是从第八级或者第九级台阶开始.也就是说已知从地面到第八级台阶一共有X种走法,从地面到第九级台阶一共有Y种走法,那么从地面到第十级台阶一共有X+Y种走法.
即F(10)=F(9)+F(8)
分析到这里,动态规划的三要素出来了.
边界:F(1)=1,F(2)=2
最优子结构:F(10)的最优子结构即F(9)和F(8)
状态转移函数:F(n)=F(n-1)+F(n-2)

// ConsoleApplication2.cpp : 定义控制台应用程序的入口点。
//
//台阶问题:有一座高度是10级台阶的楼梯,从下往上走,每跨一步只能向上1级或者2级台阶。要求用程序来求出一共有多少种走法。
#include "stdafx.h"
#include <iostream>
using namespace std;
int getResultByDP(int n)//自底向上的问题解法
{
	if (n<1)
	{
		return 0;
	}
	if (n==1)
	{
		return 1;
	}
	if (n==2)
	{
		return 2;
	}
	int a = 1;//从两个递归基开始
	int b = 2;
	int temp = 0;
	for (int i = 3; i < n + 1; i++) // 从第三阶开始,循环到题目所给阶梯数
	{
		temp = a + b;  // 在前一次走台阶时的走法数量(解法数)(如第一次循环时,此为上第三级台阶的走法数量)
		a = b;		   // 存入上一次走的走法数量  
		b = temp;	// 在下一次循环时更新当前走上台阶的走法数量
	}
	return temp;
}
int _tmain(int argc, _TCHAR* argv[])
{
	cout << getResultByDP(10);
	system("pause");
	return 0;
}

从矩阵左上角走到右下角最短路径问题

//给定一个矩阵m,从左上角开始每次只能向右走或者向下走,最后达到右下角的位置,路径中所有数字累加起来就是路径和,返回所有路径的最小路径和,如果给定的m如下,那么路径1,3,1,0,6,1,0就是最小路径和,返回12.
#include "stdafx.h"
#include <string>
#include <iostream>
#include <algorithm>
using namespace std;
int const x_length=5, y_length=5;
int m[x_length][y_length] = {
	0, 0, 0, 0, 0,
	0, 1, 3, 5, 9,
	0, 8, 1, 3, 5,
	0, 5, 0, 6, 1,
	0, 8, 8, 4, 0
};
int minDis() //m二级指针(可以是一个二维数组)
{
	int dp[4 + 1][4 + 1];
	//---------初始化边界条件-----------------
	for (size_t i = 0; i < x_length; i++)
	{
		dp[i][0] = 0;
	}
	for (size_t j = 0; j < y_length; j++)
	{
		dp[0][j] = 0;
	}
	//-------------------------------------------
	for (size_t i = 1; i < x_length; i++)
	{
		for (size_t j= 1; j < y_length; j++)
		{
			if (i == 1)
			{
				dp[i][j] = dp[i][j - 1] + m[i][j];
			}
			else if (j == 1)
			{
				dp[i][j] = dp[i - 1][j] + m[i][j];
			}
			else
			{
				int temp1 = dp[i - 1][j] + m[i][j];
				int temp2 = dp[i][j - 1] + m[i][j];
				dp[i][j] = min(temp1, temp2);
			}			
		}
	}
	return dp[x_length - 1][y_length - 1];
}
int _tmain(int argc, _TCHAR* argv[])
{
	cout << "最右下角的最短路径为:" << minDis();
	system("pause");
	return 0;
}

最大子序和
给定一个整数数组 nums ,找到一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。

#分析: 利用动态规划的思路解题: 首先寻找最优子问题,[-2,1,-3,4,-1,2,1,-5,4],第一个最优子问题为-2,那么到下一个1,其最优为当前值或者当前值加上上一个最优值,因而可以得到其递推公式
状态转移方程
dp[i] = max(nums[i], nums[i] + dp[i - 1])
解释

i代表数组中的第i个元素的位置
dp[i]代表从0到i闭区间内,所有包含第i个元素的连续子数组中,总和最大的值

nums = [-2,1,-3,4,-1,2,1,-5,4]dp = [-2, 1, -2, 4, 3, 5, 6, 1, 5]
class Solution(object):
    def maxSubArray(self, nums):
        """
        :type nums: List[int]
        :rtype: int
        """
        
#        判断边界
        if len(nums)==0:
            return 0
#         定义一个表格进行存储上一个子问题的最优解
        d=[]
        d.append(nums[0])    #第一个最优解为第一个元素
        max_=nums[0]      #返回的最大值
        for i in range(1,len(nums)):
            if nums[i]>nums[i]+d[i-1]:
                d.append(nums[i])
            else:
                d.append(nums[i]+d[i-1])
            if max_<d[i]:
                max_=d[i]
        return max_
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值