【刷题】【C++】Distinct Subsequences问题

来源:互联网 发布:淘宝达人好做吗 编辑:程序博客网 时间:2024/09/21 06:35

leetcode原地址:https://leetcode.com/problems/distinct-subsequences/

原题:

Given a string S and a string T, count the number of distinct subsequences of T in S.

A subsequence of a string is a new string which is formed from the original string by deleting some (can be none) of the characters without disturbing the relative positions of the remaining characters. (ie, "ACE" is a subsequence of "ABCDE" while "AEC" is not).

Here is an example:
S = "rabbbit"T = "rabbit"

Return 3.

Subscribe to see which companies asked this question

#include "stdafx.h"#include<iostream>#include <string>#include <cstdlib>#include <list>using namespace std;int Calculus1(string s, string t);int Calculus2(string s, string t);int main(int argc, char* argv[]){string s, t;//母串cin >> s;//子串cin >> t;//子串个数int int_Sub;//方法1int_Sub = Calculus1(s, t);cout << int_Sub<<endl;//方法2int_Sub = Calculus2(s, t);cout << int_Sub<<endl;cin.get();return 0;} //方法1,枚举法int Calculus1(string s,string t){    //堆栈,用于存放字串每个字符当前对比到的位置typedef list<int>int_list;//当前正在对比的字符串int_list point;int_list point2;//子串的个数int int_son = 0;//当前正在遍历的母串的字符位置int int_now_char = 0;int int_size_T = t.size();for (int i = 0; i < s.size(); i++){//若当前母串字符和当前子串字符吻合,将当前对比到的母串的位置压入对战,子串指针前移,未检测字符数量减1if (t[int_now_char] == s[i]){point.push_back(i);if (int_now_char < t.size()){int_now_char++;}if (int_size_T>0){int_size_T--;}//若目前已对比到子串末尾则子串数量加一,堆栈弹出,回溯至上一字符,子串指针前移一位。if (int_size_T == 0 && i != s.size() - 1){int_son++;point.pop_back();int_size_T++;int_now_char--;}//若当前同时到达母串和子串末尾,则堆栈弹出2个数字,子串数量加一,字串指针前移两位,母串指针i回溯if (int_size_T == 0 && i == s.size() - 1){int_son++;if (point.size() != 0){point.pop_back();if (point.size() != 0){int_now_char -= 2;int_size_T += 2;i = point.back();point.pop_back();}}}//若当前子串指针未到末尾,母串已到,则堆栈弹出2个数字,子串指针前移2位,母串指针回溯if (int_size_T != 0 && i == s.size() - 1){if (point.size() != 0){point.pop_back();if (point.size() != 0){int_now_char -= 2;int_size_T += 2;i = point.back();i = point.back();point.pop_back();}}}}//若当前子串不吻合,且已到达母串末尾,堆栈不为空则,母串回溯,子串指针前移一位else if ((i == s.size() - 1) && (t[int_now_char] != s[i]) && (point.size() != 0)){i = point.back();point.pop_back();int_now_char--;int_size_T++;}}return int_son;}//方法2,树形逆向相加int Calculus2(string s,string t){typedef list<int> datastack;//声明三个堆栈,两个用于存放数据串,一个用于分组标记,即子串数量即为组数datastack data1,data2,group;int int_son = 0;//当子串长度为1时if (t.size()>1){//计算组数,以及每组中每个字符串在母串中同下一个字符拥有等序位的数目for (int i = 0; i < t.length()-1; i++){int int_group = 0;for (int j = 0; j < s.length(); j++){if (t[i] == s[j]){int_group++;int enequal = 0;for (int m = j+1; m < s.length(); m++){if (t[i + 1] == s[m]){enequal++;}}data1.push_back(enequal);}}group.push_back(int_group);}//当组数大于1时while (group.size()>1){int dataL = group.back();group.pop_back();int dataF = group.back();group.pop_back();//在内存中位两组数据动态分配存储空间,存入一个数组当中int * cacheL = (int *)malloc(dataL * sizeof(int));int * cacheF = (int *)malloc(dataF * sizeof(int));for (int i = 0; i < dataL; i++){*(cacheL+i) = data1.back();data1.pop_back();}for (int i = 0; i < dataF; i++){*(cacheF+i) = data1.back();data1.pop_back();}//对比数组中的数据,将后组位置比前组数组中保存数字小的数据相加放入第二堆栈中for (int i = 0; i < dataF; i++){int cache = 0;for (int j = 0; j < *(cacheF + i); j++){cache += *(cacheL+ j);}data2.push_back(cache);}//销毁内存分配防止内存溢出free(cacheL);free(cacheF);//将堆栈2中的数据统计压入,分组堆栈group.push_back(data2.size());//将第二堆栈中的数据再次放入堆栈一种while (data2.size()>0){data1.push_back(data2.back());data2.pop_back();}//当组仅剩一组时,全部相加while (group.size() == 1){while (data1.size() > 0){int_son += data1.back();data1.pop_back();}group.pop_back();}}//若只有一组分组,则直接全部相加while (group.size()==1){while (data1.size()>0){int_son += data1.back();data1.pop_back();}group.pop_back();}}//若子串仅有一个字符则对比相同的字符全部相加else{for (int i = 0; i < s.length();i++){if (s[i] == t[0]){int_son++;}}}return int_son;}

可以看到上面有两个方法,方法一是枚举法,但是在长串运算的时候,会因为数量巨大而需要大量时间,无法再规定时间内完成运算。所以最后采用树形逆向相加的策略来完成这个题目。


在编程过程中遇到的问题:

1. malloc函数是以byte为单位来分配内存的,如果不在调用中*sizeof(type)的话,在free的过程中会被强行中断。

2. stack的back()函数只会返回栈顶数据,需要用pop_back()函数来做弹出操作。

3.算法的设计上必须考虑时间复杂度,否则就会在oj的时候出现timeout的情况。


测试用例:

“bbb” “bb”   3

"12341132413422132453" "1234"    27

"b" "b" 1

""  "a"  0

"aabdbaabeeadcbbdedacbbeecbabebaeeecaeabaedadcbdbcdaabebdadbbaeabdadeaabbabbecebbebcaddaacccebeaeedababedeacdeaaaeeaecbe"
"bddabdcae"   10582116


最后附上书面草稿



0 0