leetcode 刷题笔记&心得【c++】【每日一题】

第一题
vector 是一个int向量,添加元素: 向量名.push_back(被添加的元素)
c++ 获取数组元素数量用nums.size() 用 sizeof(nums)/sizeof(int) leetcode报错说内存消耗
map.count(Key)返回值为1或者0,1返回存在,0返回不存在

方法1:两个嵌套for
方法2:先将key-value 存入map (一个for),用targrt-nums[i]去判断该值是否在key中可以被找到(map.count,其实应该也是相当于一个for)。个人认为该方法还不如暴力来的好。
方法3: 一个map(不用添加元素)nums每一个元素都去map找是否有满足targrt-nums[i]的元素),这样map.count就不是在所有元素中遍历了,该方法的时间复杂度小于O(N2)。

第二题
我的代码是这样的,然而看了一下题解,发现我好菜啊,而且我的执行还不通过。
有的人简化了案例给出了一种解法更加简单明了。


/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */
class Solution {
public:
    ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
        
        ListNode* result;
        ListNode* p;
        ListNode* p1;
        ListNode* p2;
        int max_count,i,j,k = 0;
        int* r1;//数组存放个位
        int* r2;//存放进位
        //声明递归函数

        
        //判断结果链表的长度
        p = l1;
        for(i = 0; p != NULL; i++)
        {
            p = p->next;
        }
        p = l2;
        for(j = 0; p != NULL; j++)
        {
            p = p->next;
        }
        max_count = i>j ? i:j;
        //计算result链表
        p = result;
        p1 = l1;
        p2 = l2;
        //搞定头节点
        p->next = (ListNode *)malloc(sizeof(ListNode));
        if(p1->val + p2->val >= 10)
        {
            p->val = p1->val + p2->val - 10;
            p->next->val = 1;
        }
        else
        {
            p->val = p1->val + p2->val ;
            p->next->val = 0;
        }
        //搞定其余节点
        for(k = 0;i<max_count+1;k++) //+1是避免最后两个相加进位
        {
            p = p->next;
            p1 = p1->next;
            p2 = p2->next;
            p->next = (ListNode *)malloc(sizeof(ListNode));
            if(p1 != NULL && p2 != NULL)
            {
                if(p1->val + p2->val + p->val >= 10)
                {
                    p->val = p1->val + p2->val + p->val- 10;
                    p->next->val = 1;
                }
                else
                {
                    p->val = p1->val + p2->val + p->val ;
                    p->next->val = 0;
                }
            }
            else
            {
                if(p1 != NULL)
                {
                    p->val = p->val + p1->val;
                }
                else
                {
                    p->val = p->val + p2->val;
                }
                p->next->val = 0;
            } 
        }   
        return result;
    }

};
/**别人的方法
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */

class Solution {
public:
    ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
        ListNode* head=new ListNode(-1);//存放结果的链表
        ListNode* h=head;//移动指针
        int sum=0;//每个位的加和结果
        bool carry=false;//进位标志
        while(l1!=NULL||l2!=NULL)
        {
            sum=0;
            if(l1!=NULL)
            {
                sum+=l1->val;
                l1=l1->next;
            }
            if(l2!=NULL)
            {
                sum+=l2->val;
                l2=l2->next;
            }
            if(carry)
                sum++;
            h->next=new ListNode(sum%10);
            h=h->next;
            carry=sum>=10?true:false;
        }
        if(carry)
        {
            h->next=new ListNode(1);
        }
        return head->next;
    }
};

第三题
第三题是我花了两个晚上搞出来的,没看题解,就是不停的提交,修改逻辑然后实现了要求,第一次击败了那么多人。
在这里插入图片描述

#include "Solution.h"


int Solution :: lengthOfLongestSubstring(string s) {
    //声明变量
    const char* str;
    const char* head;
    const char* tail;
    const char* temp;
    int len = 0;
    int max_len = 0;
    bool flag = false;

    //类转char数组
    str = s.c_str();

    //实例化指针
    head = tail = temp = str;

    if (s.empty())
    {
        return 0; //字符串为空返回0
    }
    else
    {
        max_len = len = 1;//不空意味着至少有一个元素
        head = &str[0];
        tail = &str[1];
        while (*tail != '\0')
        {
            //看看新加入的元素是否和之前重复
            for (temp = head; temp < tail; )
            {
                if (*tail == *temp)
                {
                    flag = true; //发现重复项
                    break;
                }
                else
                {
                    temp++;//未发现重复项就自加
                }
            }

            if (flag)
            {
                flag = false;
                head = ++temp; //i++先赋值再自加,++i先自加,再赋值
                tail++;
                max_len = max_len > len ? max_len : len;
                if (*tail == '\0')
                {
                    break;
                }
                else
                {
                    len = tail - head;
                }
            }
            else
            {
                tail++;
                len++;
                max_len = max_len > len ? max_len : len;
            }
        }
    }
    return max_len;
}

第四题

在这里插入图片描述
该题花了两个晚上,我比较一般,用的方法都是按照正常人的思维来解题的。

class Solution {
public:
    double findMedianSortedArrays(vector<int>& nums1, vector<int>& nums2)
 {
    int m = nums1.size();//数组1的长度
	int n = nums2.size();//数组2的长度
	int p;

	//当前需要判断数组的长短,短的数组的元素插到长的数组
	if (m>=n) 
	{
		if (nums2.empty())
		{
			if (nums1.empty())
			{
				return 0;
			}
			if (m%2 == 0)//偶数,取中位数 
			{
				return ((double)nums1[m / 2 - 1] + (double)nums1[m / 2])/2;
			}
			else
			{
				return (double)nums1[m / 2];
			}
		}
		//nums2插入nums1
		while (!nums2.empty())
		{
			p = nums2[0];
			nums2.erase(nums2.begin());
			insert(nums1,p);
		}

		//取中位数
		m = nums1.size() ;
		if (m % 2 == 0)//偶数,取中位数 
		{
			return (double)(nums1[m / 2 - 1] + (double)nums1[m / 2]) / 2;
		}
		else
		{
			return (double)nums1[m / 2];
		}
		
	}
	else
	{
		if (nums1.empty())
		{
			if (nums2.empty())
			{
				return 0;
			}
			if (n % 2 == 0)//偶数,取中位数 
			{
				return ((double)nums2[n / 2 - 1] + (double)nums2[n / 2]) / 2;
			}
			else
			{
				return (double)nums2[n / 2];
			}
		}
		//nums1插入nums2
		while (!nums1.empty())
		{
			p = nums1[0];
			nums1.erase(nums1.begin());
			insert(nums2, p);
		}

		//取中位数
		n = nums2.size() ;
		if (n%2 == 0)//偶数,取中位数 
		{
			return ((double)nums2[n / 2 - 1] + (double)nums2[n / 2]) / 2;
		}
		else
		{
			return (double)nums2[n / 2];
		}
	}
    }
private :
    void insert(vector<int>& num, int p)
{
	int low;
	int high;
	int mid;

	low = 0;
	high = num.size()-1;

	while (low <= high)
	{
		mid = (low + high+1) / 2;
		if (num[mid] == p)
		{
            low = mid;
			break;
		}
		else if (num[mid] > p)
		{
			high = mid - 1;
		}
		else
		{
			low = mid + 1;
		}
	}
	num.insert(num.begin() + low, p);

}
};

第五题

实在是做不出来,一开始以为可以很快出结果,后面心态就炸了。
这个代码是跑不出来的。

#include "longestPalindrome.h"


string Solution::longestPalindrome(string s)
{
	string res = "";
	string temp;
	int len = s.length();
	bool flag = false; //用来判断是否属于左右对称的类型
	int p = 1;
	int i = 1;

	//len == 1 ; len == 2 的情况单独算
	if (len == 1)
	{
		res = s;
		return res;
	}

	if (len == 2)
	{
		if (s[0] == s[1])
		{
			res = s;
		}
		else
		{
			res = s[0];
		}
		return res;
	}

	while (p < len)
	{
		while (p - i >= 0 && p + i < len)
		{
			if (s[p - i] == s[p + i])//以某个数为中心两边对称
			{
				if ((i * 2 + 1) > res.length())
					res = s.substr(p - i, i * 2 + 1);
				i++;
				flag = true;

			}
			else
			{
				if (!flag) //意味着不属于两边对称的情况
				{
					if (s[p] == s[p + 1] && 2 >= res.length()) //看看能不能和右边的元素相等
						res = s.substr(p, 2);
					if (s[p] == s[p - 1] && 2 >= res.length())//看看能不能和左边的元素相等
						res = s.substr(p - 1, 2);
					if (1 > res.length()) //左右不相等,而且res为""
						res = s[p];
				}

				break;
			}
		}

		//避免因为一侧越界导致另一侧没被算入res
		if (res.length()%2 == 1)
		{
			int j = 0;
			while (j + 1 < res.length())
			{
				if (res[0] == res[j + 1])
				{
					j++;
				}
				else
				{
					break;
				}

			}

			if (res.length() < len && j + 1 == res.length() && j != 0)
			{
				if (p - i >= 0)
				{
					if (s[p - i] == res[0])
					{
						res = res + s[p - i];
					}
				}
				else if (p + i < len)
				{
					if (s[p + i] == res[0])
					{
						res = res + s[p + i];
					}
				}
			}
		}
		
		
		p++;
		i = 1;
	}

	return res;
}





第八题

class Solution {
public:
    int myAtoi(string s) {
        char negFlag = 1;
	int i = 0;
	char errState = 0; //0字符串为纯数字  1字符串不是纯数字
	int p = 0;
	double ret = 0;
	if (!s.empty())
	{
		s.erase(0, s.find_first_not_of(" "));
		s.erase(s.find_last_not_of(" ") + 1);
		//cout << s << endl; //清空空格
		//cout << s[0] << endl;
		char* numSave = (char*)malloc(sizeof(char) * s.size());

		//分为有符号和无符号的三种情况
		if (s[0] == '-')
		{
			negFlag = -negFlag;
			i = 1;
		}
		else if (s[0] == '+')
		{
			i = 1;
		}
		else
		{
			i = 0;
		}

		//字符转换成数字
		for (; i < s.size(); i++)
		{
			if (s[i] >= 48 && s[i] <= 57) // ASCII 48-57对应 ‘0’-‘9’
			{
				numSave[p] = s[i]-48;
				p++;
			}
			else
			{
				if ((s[0] == '-' || s[0] == '+') && i>1) //带符号的情况下存在数字
				{
					break;
				}
				else if (i>0)//不带符号的情况下存在数字
				{
					break;
				}
				else //一开始就不存在数字
				{
					errState = 1;
					break;
				}
				
			}

		}

		if (errState)
		{
			free(numSave);
			return 0;
		}

		for (p--,i = 0; p>=0; p--,i++)
		{
			ret +=(double) (numSave[p] * pow(10,i));
		}
		free(numSave);
		if ((double)negFlag * ret < -2147483648)
		{
			return -2147483648;
		}
		if (negFlag * ret > 2147483647)
		{
			return 2147483647;
		}
		return (int)negFlag*ret;
	}
	return 0;
    }
};

第九题

这题参考了之前数字逆排的思路,当时那题我也是用递归先做了一遍,然后采用的是while方法。
不过我这种方法击败的人很少。

h文件
#ifndef SOLUTION_H
#define SOLUTION_H
#include "stdlib.h"
#include <iostream>
using namespace std;
class Solution
{
public:
    typedef struct
    {
        int count;
        char* array;
    }Array_ntoa;

public:
    bool isPalindrome(int x);
    bool fun(int x, Array_ntoa* y);

};


#endif // !SOLUTION_H


c文件
#include "Solution.h"

# define INITSIZE 3

bool Solution::isPalindrome(int x)
{
	Array_ntoa y;
	y.count = 0;
	y.array = (char*)malloc(sizeof(char) * INITSIZE);
	if (!y.array)
	{
		exit(1);
	}
	if (x<0)
	{
		return false;
	}

	while (x!=0)
	{
		
		if (y.count >= INITSIZE)
		{
			y.array =(char*) realloc(y.array,y.count+1);
		}
		y.array[y.count] = x % 10;
		y.count++;
		x = x / 10;
	}

	for (int i = 0; i < y.count/2; i++)
	{
		if (y.array[0+i] != y.array[y.count-1-i])
		{
			return false;
		}
	}

	free(y.array);
	return true;
}

//递归函数

bool Solution::fun(int x, Array_ntoa *y_struct)
{
	/*	if (x <= 0)
	{
		return false;
	}
	else 
	{
		if (fun(x / 10, y_struct))
		{
			y_struct->array[y_struct->count] = x % 10;
			y_struct->count++;
			return true;
		}
		else
		{
			y_struct->array[y_struct->count] = x % 10;
			y_struct->count++;
			return true;
		}
		
	}*/
	return true;
}

主函数
#include "Solution.h"
#include "stdio.h"
#include "stdlib.h"


void main()
{

	Solution s;
	if (s.isPalindrome(10))
	{
		printf("yes");
	}
	else
	{
		printf("no");
	}

}
























评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

鄢广杰

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值