日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

LeetCode——字节跳动系列题目

發(fā)布時間:2024/3/13 编程问答 48 豆豆
生活随笔 收集整理的這篇文章主要介紹了 LeetCode——字节跳动系列题目 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

轉(zhuǎn)至:https://blog.csdn.net/Uupton/article/details/84640146

今天登陸leetcode發(fā)現(xiàn)探索區(qū)多了字節(jié)跳動的專欄,特意用了一下午去刷,有些是之前刷過的。但題目不錯,就當(dāng)是復(fù)習(xí)一遍吧,這里記錄一下我會的以及自己覺得不錯的題目。

原題鏈接請點擊題目

一:挑戰(zhàn)字符串

3. 無重復(fù)字符的最長子串

分析:這題要求連續(xù)的不重復(fù)的最長子序列的長度,注意這里是需要連續(xù),利用這個特性,我們可以維護(hù)一個窗口,窗口裝的是無重復(fù)的字符串,一開始窗口的左邊在起點(即下標(biāo)為0處)。我們用 i 遍歷字符串,如果當(dāng)前字符沒有出現(xiàn)過或者當(dāng)前字符雖然出現(xiàn)過但不在當(dāng)前的窗口,則窗口向右擴張。而當(dāng)當(dāng)前字符出現(xiàn)在窗口內(nèi),則窗口的左邊收縮到當(dāng)前字符前一個出現(xiàn)的位置。詳見代碼

  • class Solution {
  • public:
  • int lengthOfLongestSubstring(string s) {
  • //維護(hù)一個滑動窗口,最大的窗口大小即為結(jié)果
  • int hash[128] = {0};
  • int left = 0,res = 0;
  • for(int i = 0;i<s.size();i++)
  • {
  • if(hash[s[i]] == 0||hash[s[i]]<left) //1:沒出現(xiàn)過 2:出現(xiàn)過但沒在窗口內(nèi)
  • res = max(res,i-left+1); //不斷更新res值
  • else
  • left = hash[s[i]]; //窗口內(nèi)出現(xiàn)重復(fù),縮小左邊窗口
  • hash[s[i]] = i+1;
  • }
  • return res;
  • }
  • };
  • 14. 最長公共前綴

    簡單題,以第一個字符串作為模版,逐個拿出模版的每個字符,然后其余的字符串也逐個拿出相對應(yīng)位置的字符比較是否相同。注意字符串長度的問題即可。

  • class Solution {
  • public:
  • string longestCommonPrefix(vector<string>& strs) {
  • if(strs.empty()) return "";
  • string res = "";
  • for(int i = 0;i<strs[0].size();i++)
  • {
  • char c = strs[0][i]; //逐個拿出模版字符串的字符
  • for(int j = 1;j<strs.size();j++) //后面的字符串
  • {
  • if(i>=strs[j].size()||strs[j][i]!=c) //當(dāng)i已經(jīng)超過字符串的長度或者字符不相同時直接返回
  • return res;
  • }
  • res+=c;
  • }
  • return res;
  • }
  • };
  • 567. 字符串的排列

    分析:對s2全排再一一跟s1對比肯定會超時。所以我們可以維護(hù)兩個窗口,一個窗口裝s1,另一個窗口裝s2。假設(shè)s1長度為len1,s2長度為len2。開始先分別裝s1和s2的前l(fā)ne1個字符進(jìn)各自的窗口。如果此時兩個窗口相等則直接返回true,如果不等則s2的窗口從len1開始裝s2的字符,同時窗口的左邊要刪除一個元素,因為兩個窗口要保持大小,期間如果兩個窗口相等則返回true

  • class Solution {
  • public:
  • bool checkInclusion(string s1, string s2) {
  • //v1、v2維護(hù)一個大小相同的窗口,先計算出len1前的字符出現(xiàn)的次數(shù),如果相等直接返回TURE,如果不等則操作v2繼續(xù)往后走,后面的字符添上,窗口左邊的字符刪除
  • int len1 = s1.size(),len2 = s2.size();
  • vector<int> v1(128,0),v2(128,0);
  • for(int i = 0;i<len1;i++)
  • {
  • v1[s1[i]]++;
  • v2[s2[i]]++;
  • }
  • if(v1==v2) return true;
  • for(int i = len1;i<len2;i++) //v2從len1位置開始裝
  • {
  • v2[s2[i]]++; //裝新的字符
  • v2[s2[i-len1]]--; //刪除早裝入的字符
  • if(v1 == v2)
  • return true;
  • }
  • return false;
  • }
  • };
  • 43. 字符串相乘

    分析:這里主要開了三個數(shù)組來做,一個數(shù)組存第一個字符串,另一個數(shù)組存第二個字符串,最后一個數(shù)組存結(jié)果。保存兩個字符串的時候要反著順序存,因為我們平時做乘法的時候也是從數(shù)字的最后一位向前乘的,所以其實這道題主要是模擬了平時在紙上做的乘法。

  • class Solution {
  • public:
  • string multiply(string num1, string num2) {
  • int x[120] = {0},y[120] = {0},z[250] = {0};
  • int len1 = num1.size(),len2 = num2.size();
  • for(int i = len1-1,k = 0;i>=0;i--)
  • x[k++] = num1[i]-'0';
  • for(int i = len2-1,k = 0;i>=0;i--)
  • y[k++] = num2[i]-'0';
  • for(int i = 0;i<len1;i++) //在這里進(jìn)行相乘,但沒進(jìn)位
  • {
  • for(int j = 0;j<len2;j++)
  • z[i+j] += (x[i]*y[j]);
  • }
  • for(int i = 0;i<249;i++) //現(xiàn)在進(jìn)位
  • {
  • if(z[i]>9)
  • {
  • z[i+1] += z[i]/10;
  • z[i]%=10;
  • }
  • }
  • int i;
  • for(i = 249;i>=0;i--)
  • if(z[i] != 0)
  • break;
  • string res = "";
  • for(;i>=0;i--)
  • res+=(z[i]+'0');
  • if(res == "") return "0";
  • return res;
  • }
  • };
  • ?

    151. 翻轉(zhuǎn)字符串里的單詞

    分析:主要做法就是先把整個字符串反轉(zhuǎn),然后開始遍歷字符串,每遍歷完一個單詞(注意不是一個字符)的時候?qū)⑦@個單詞再反轉(zhuǎn)。

  • class Solution {
  • public:
  • void reverseWords(string &s) {
  • int index = 0,n = s.size();
  • reverse(s.begin(),s.end()); //反轉(zhuǎn)整個字符串
  • for(int i = 0;i<n;i++)
  • {
  • if(s[i]!=' ') //遇到非空格的字符
  • {
  • if(index!=0)
  • s[index++] = ' ';
  • int j = i; //令j = i 進(jìn)行下面的操作
  • while(j<n&&s[j]!=' ') //遍歷完整一個單詞
  • s[index++] = s[j++];
  • reverse(s.begin()+index-(j-i),s.begin()+index); //對剛才遍歷的單詞進(jìn)行反轉(zhuǎn)
  • i = j;
  • }
  • }
  • s.resize(index);
  • }
  • };
  • 93. 復(fù)原IP地址

    分析:一般題目問字符串有多少種可能的排列,十有八九都是用遞歸做的。我們需要先寫一個函數(shù)判斷一個字符串是否符合ip其中一個結(jié)點,符合的標(biāo)準(zhǔn):1、1到3位長度的字符串。2、長度大于一的話首位不能為0。3、整數(shù)大小要在0~255的范圍內(nèi)。

    接著就可以遞歸做正式工作。這里對字符串分別截取一位、二位、三位。。。判斷是否能構(gòu)成ip的一個結(jié)點,如果能的話就截斷這部分,讓剩余的部分遞歸下去繼續(xù)做判斷。

    具體看代碼

  • class Solution {
  • public:
  • vector<string> restoreIpAddresses(string s) {
  • vector<string> res;
  • // string out = "";
  • helper(res,s,"",4);
  • return res;
  • }
  • void helper(vector<string>& res,string s,string out,int k)
  • {
  • if(k==0)
  • {
  • if(s.empty()) //注意點一,原字符串s應(yīng)該要為空了
  • res.push_back(out);
  • }
  • else
  • {
  • for(int i = 1;i<=3;i++)
  • {
  • //截取某部分進(jìn)行判斷,如果合法則進(jìn)入下一個遞歸
  • if(s.size()>=i&&isValid(s.substr(0,i))) //注意點二,越界判斷
  • {
  • if(k==1) //k==1代表當(dāng)前ip再添加多一個結(jié)點就夠四個了
  • helper(res,s.substr(i),out+s.substr(0,i),k-1);
  • else
  • helper(res,s.substr(i),out+s.substr(0,i)+'.',k-1);
  • }
  • }
  • }
  • }
  • //判斷是否合法
  • bool isValid(string s)
  • {
  • if(s.empty()||s.size()>3||(s.size()>1&&s[0]=='0'))
  • return false;
  • int num = atoi(s.c_str());
  • return num>=0&&num<=255;
  • }
  • };
  • 二、數(shù)組與排序

    15. 三數(shù)之和

  • class Solution {
  • public:
  • vector<vector<int>> threeSum(vector<int>& nums) {
  • vector<vector<int>> res;
  • sort(nums.begin(),nums.end());
  • for(int i = 0;i<nums.size();i++)
  • {
  • if(nums[i]>0) break;
  • if(i>0&&nums[i] == nums[i-1])
  • continue;
  • int target = 0-nums[i];
  • int j = i+1,k = nums.size()-1;
  • while(j<k)
  • {
  • if(nums[j]+nums[k] == target)
  • {
  • res.push_back({nums[i],nums[j],nums[k]});
  • while(j<k&&nums[j+1] == nums[j]) j++;
  • while(j<k&&nums[k-1] == nums[k]) k--;
  • j++;k--;
  • }
  • else if(nums[j]+nums[k]<target)
  • j++;
  • else
  • k--;
  • }
  • }
  • return res;
  • }
  • };
  • ?

    674. 最長連續(xù)遞增序列

  • class Solution {
  • public:
  • int findLengthOfLCIS(vector<int>& nums) {
  • int res = 0,cnt = 0;
  • int cur = INT_MAX;
  • for(int num:nums)
  • {
  • if(num>cur)
  • cnt++;
  • else cnt = 1;
  • res = max(res,cnt);
  • cur = num;
  • }
  • return res;
  • }
  • };
  • ?

    三、鏈表與樹

    2. 兩數(shù)相加

  • /**
  • * Definition for singly-linked list.
  • * struct ListNode {
  • * int val;
  • * ListNode *next;
  • * ListNode(int x) : val(x), next(NULL) {}
  • * };
  • */
  • class Solution {
  • public:
  • ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
  • int add = 0;
  • ListNode* res = new ListNode(0);
  • ListNode* head = res;
  • while(l1||l2||add)
  • {
  • int num = (l1?l1->val:0)+(l2?l2->val:0)+add;
  • head->next = new ListNode(num%10);
  • head = head->next;
  • add = num/10;
  • l1 = l1?l1->next:l1;
  • l2 = l2?l2->next:l2;
  • }
  • return res->next;
  • }
  • };
  • ?

    148. 排序鏈表

  • /**
  • * Definition for singly-linked list.
  • * struct ListNode {
  • * int val;
  • * ListNode *next;
  • * ListNode(int x) : val(x), next(NULL) {}
  • * };
  • */
  • class Solution {
  • public:
  • ListNode* sortList(ListNode* head) {
  • if(!head||!head->next) return head;
  • ListNode* slow = head,*fast = head,*pre = head;
  • while(fast&&fast->next)
  • {
  • pre = slow;
  • slow = slow->next;
  • fast = fast->next->next;
  • }
  • pre->next = NULL;
  • return merge(sortList(head),sortList(slow));
  • }
  • ListNode* merge(ListNode* a,ListNode* b)
  • {
  • ListNode* head = new ListNode(0);
  • ListNode* node = head;
  • while(a&&b)
  • {
  • if(a->val<b->val)
  • {
  • node->next = a;
  • a = a->next;
  • }
  • else
  • {
  • node->next = b;
  • b = b->next;
  • }
  • node = node->next;
  • }
  • if(a) node->next = a;
  • if(b) node->next = b;
  • return head->next;
  • }
  • };
  • ?

    142. 環(huán)形鏈表 II

  • /**
  • * Definition for singly-linked list.
  • * struct ListNode {
  • * int val;
  • * ListNode *next;
  • * ListNode(int x) : val(x), next(NULL) {}
  • * };
  • */
  • class Solution {
  • public:
  • ListNode *detectCycle(ListNode *head) {
  • ListNode* fast = head;
  • ListNode* slow = head;
  • while(fast&&fast->next)
  • {
  • slow = slow->next;
  • fast = fast->next->next;
  • if(slow == fast)
  • break;
  • }
  • if(!fast||!fast->next) return NULL;
  • slow = head;
  • while(fast != slow)
  • {
  • slow = slow->next;
  • fast = fast->next;
  • }
  • return fast;
  • }
  • };
  • ?

    236. 二叉樹的最近公共祖先

  • /**
  • * Definition for a binary tree node.
  • * struct TreeNode {
  • * int val;
  • * TreeNode *left;
  • * TreeNode *right;
  • * TreeNode(int x) : val(x), left(NULL), right(NULL) {}
  • * };
  • */
  • class Solution {
  • public:
  • TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
  • if(!root||p==root||q==root) return root;
  • TreeNode* left = lowestCommonAncestor(root->left,p,q);
  • TreeNode* right = lowestCommonAncestor(root->right,p,q);
  • if(left&&right) //p和q分別位于左右子樹中
  • return root;
  • return left?left:right;
  • }
  • };
  • ?

    四、動態(tài)或貪心

    121. 買賣股票的最佳時機

  • class Solution {
  • public:
  • int maxProfit(vector<int>& prices) {
  • int res = 0,buy = INT_MAX;
  • for(auto c:prices)
  • {
  • buy = min(buy,c);
  • res = max(res,c-buy);
  • }
  • return res;
  • }
  • };
  • ?

    122. 買賣股票的最佳時機 II

  • class Solution {
  • public:
  • int maxProfit(vector<int>& prices) {
  • int len = prices.size();
  • if(len<=1)
  • return 0;
  • vector<int> have(len);
  • vector<int> unhave(len);
  • have[0] = -prices[0];
  • int res = 0;
  • for(int i = 1;i<len;i++)
  • {
  • unhave[i] = max(unhave[i-1],have[i-1]+prices[i]);
  • have[i] = max(have[i-1],unhave[i-1]-prices[i]);
  • res = max(res,unhave[i]);
  • }
  • return res;
  • }
  • };
  • ?

    221. 最大正方形

  • class Solution {
  • public:
  • int maximalSquare(vector<vector<char>>& matrix) {
  • if(matrix.empty()||matrix[0].empty()) return 0;
  • int m = matrix.size(),n = matrix[0].size();
  • vector<vector<int>> dp(m,vector<int>(n,0));
  • int res = 0;
  • for(int i = 0;i<m;i++)
  • {
  • for(int j = 0;j<n;j++)
  • {
  • if(i == 0||j == 0)
  • dp[i][j] = matrix[i][j]-'0';
  • else if(matrix[i][j] == '1')
  • dp[i][j] = min(min(dp[i-1][j-1],dp[i-1][j]),dp[i][j-1])+1;
  • res = max(res,dp[i][j]);
  • }
  • }
  • return res*res;
  • }
  • };
  • ?

    ?

    總結(jié)

    以上是生活随笔為你收集整理的LeetCode——字节跳动系列题目的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。