准备
博主:大大怪先森(记得关注,下次不要迷路哦) 编程环境:vs2013
前言
算法训练第二天!!! 让我们一步一步的成为大佬!!! 心中有梦,以梦为马,志存远方,不负韶华。
提示:以下是本篇文章正文内容
一、数组中出现次数超过一半的数字
题目描述
给一个长度为 n 的数组,数组中有一个数字出现的次数超过数组长度的一半,请找出这个数字。例如输入一个长度为9的数组[1,2,3,2,2,2,5,4,2]。由于数字2在数组中出现了5次,超过数组长度的一半,因此输出2。 要求:空间复杂度:O(1),时间复杂度 O(n)
oj链接:https://www.nowcoder.com/practice/e8a1b01a2df14cb2b228b30ee6a92163?
题目分析
解法: 思路一:使用map,利用map<数字,次数>的映射关系,最后统计数字出现的次数 思路二:先将数组排序,超过一半的数字一定是在中间的那个数. 思路三(附图解):目标条件:目标数据超过数组长度的一半,那么对数组,我们同时去掉两个不同的数字,到最后剩下的一个数就是该数字。 简单来说:就是从第一个数字开始和后面的数字比较一样的话就将第一个数字和那个不同意的数字去掉相同的数字保留,然后依次类推让第二个数字和后面的数字比较相同就保留不同就去掉最后留下来的数字一定就是过半的那个数字
代码解析
思路一(代码):
unordered_map<int, int> map;
int half = numbers.size()/2;
for(int i = 0; i < numbers.size(); i++){
auto it = map.find(numbers[i]);
if( it != map.end() ){
map[numbers[i]]++;
}
else{
map.insert(make_pair(numbers[i], 1));
}
if(map[numbers[i]] > half){
return numbers[i];
}
}
return 0;
}
思路二(代码):
class Solution {
public:
int MoreThanHalfNum_Solution(vector<int> numbers) {
sort(numbers.begin(), numbers.end());
int count = 0;
int min = 0;
if(numbers.size() == 1)
{
return numbers[0];
}
min = numbers.size() >> 1;
for(int i = 0;i < numbers.size();i++)
{
if(numbers[min] == numbers[i])
{
count++;
}
}
if(count > min)
{
return numbers[min];
}
return -1;
}
};
思路三(代码):
class Solution {
public:
int MoreThanHalfNum_Solution(vector<int> numbers) {
if(numbers.size() == 0)
{
return -1;
}
int number = numbers[0];
int times = 1;
for(int i = 1;i < numbers.size();i++)
{
if(times == 0)
{
number = numbers[i];
times++;
}
if(number == numbers[i])
{
times++;
}
else
{
times--;
}
}
int count = 0;
for(int i = 0;i < numbers.size();i++)
{
if(number == numbers[i])
{
count++;
}
}
return count > (numbers.size() >> 1)? number:-1;
}
};
二、字符替换
题目描述
请实现一个函数,将一个字符串中的每个空格替换成“%20”。例如,当字符串为We Are Happy.则经过替换之后的字符串为We%20Are%20Happy。
oj链接:https://www.nowcoder.com/practice/4060ac7e3e404ad1a894ef3e17650423?
题目分析
有空格就需要将原来的字符串的大小扩充2个位置安放%20 故:n个空格扩充n * 2个位置 注意访问的顺序是:从后向前
代码解析
代码如下(示例):
class Solution {
public:
void replaceSpace(char* str, int length) {
int count = 0;
char* start = str;
while (*start) {
if (isspace(*start)) {
count++;
}
start++;
}
char* old_end = str + length;
char* new_end = str + length + 2 * count;
while (old_end >= str && new_end >= str) {
if (!isspace(*old_end)) {
*new_end = *old_end;
new_end--, old_end--;
} else{
*new_end-- = '0';
* new_end-- = '2';
* new_end-- = '%';
old_end--;
}
}
}
};
从尾到头打印链表
题目描述
输入一个链表的头节点,按链表从尾到头的顺序返回每个节点的值(用数组返回)。 如输入{1,2,3}的链表如下图:
oj链接:https://www.nowcoder.com/practice/d0267f7f55b3412ba93bd35cfa8e8035?
题目分析
思路一:创建栈,利用栈先进后出的特点. 思路二:创建一个数组,将链表的数值保存在数组中,然后再逆置数组 思路三(附图解):递归(重点讲解)
代码解析
思路一:
class Solution {
public:
vector<int> printListFromTailToHead(ListNode* head) {
stack<int> s;
vector<int> v;
while(head){
s.push(head->val);
} w
hile(!s.empty()){
v.push_back(s.top());
s.pop();
} r
eturn v;
}
};
思路二:
class Solution {
public:
vector<int> printListFromTailToHead(ListNode* head) {
vector<int> v;
while(head)
{
v.push_back(head->val);
head = head->next;
}
reverse(v.begin(),v.end());
return v;
}
};
思路三:
class Solution {
public:
void reverseList(ListNode* head,vector<int>& v)
{
if(head == nullptr)
{
return;
}
reverseList(head->next,v);
v.push_back(head->val);
}
vector<int> printListFromTailToHead(ListNode* head) {
vector<int> v;
reverseList(head,v);
return v;
}
};
重建二叉树(较难)
题目描述
给定节点数为 n 的二叉树的前序遍历和中序遍历结果,请重建出该二叉树并返回它的头结点。例如输入前序遍历序列{1,2,4,7,3,5,6,8}和中序遍历序列{4,7,2,1,5,3,8,6},则重建出如下图所示。
oj链接:https://www.nowcoder.com/practice/8a19cbe657394eeaac2f6ea9b0f6fcf6?
题目分析
递归 给出一个二叉树的前序和中序我们便可以确定一个二叉树,首先找出二叉树的根节点然后找出二叉树的左右子数,在左右子数中再次找出根节点和左右子树,依次递归下去重建一个二叉树 图解:
代码分析
class Solution {
public:
TreeNode* reConstructBinaryTreeCore(vector<int> pre,int preStart,int preEnd,
vector<int> vin, int vinStart, int vinEnd){
if(preStart > preEnd || vinStart > vinEnd)
{
return nullptr;
}
TreeNode* root = new TreeNode(pre[preStart]);
for(int i = 0;i < vin.size();i++)
{
if(pre[preStart] == vin[i])
{
root->left = reConstructBinaryTreeCore(pre,preStart + 1,preStart + i - vinStart,
vin,vinStart,i - 1);
root->right = reConstructBinaryTreeCore(pre,preStart + i - vinStart + 1,preEnd,
vin,i + 1,vinEnd);
break;
}
}
return root;
}
TreeNode* reConstructBinaryTree(vector<int> pre,vector<int> vin) {
if (pre.empty() || vin.empty())
{
return nullptr;
}
return reConstructBinaryTreeCore(pre, 0, pre.size()-1, vin, 0, vin.size()-1);
}
};
结语
希望本篇文章能给各位带来帮助,如有不足还请指正!!!
码字不易,各位大大给个收藏点赞吧!!!
|