Topcoder SRM 630div 2

A:不断的消除两个相邻的相等字符,简单题。

真心不习惯STL。。

#include<iostream>
#include <string>
#include <vector>
using namespace std;
class DoubleLetter {
    public:
    string ableToSolve(string S) {
    while (1){
    int flag=0;
    for (int i=1;i<S.size();i++)
    if (S[i]==S[i-1])
    {
       S.erase(i-1,2);
       flag=1;
    }
    if (!flag||S.size()==0) break;
    }
    if (S.size()==0) return "Possible";
    else return "Impossible";
    }
};

// Powered by FileEdit
// Powered by TZTester 1.01 [25-Feb-2003]
// Powered by CodeProcessor

B:给出有N个节点一棵树,求在M个两两的点距离相等求出最大的M值(N<=10);

先FLoyd求出所有点与点之间的距离。

然后用类似状态压缩DP的方式枚举满足的方案。

然后比较出最大值。

#include<iostream>
#include <string>
#include <vector>
#include<string.h>
using namespace std;
int b[12345];
int dis[12][12];
int mp[12][12];

class Egalitarianism3Easy {
    public:
    int maxCities(int n, vector <int> a, vector <int> b, vector <int> len) {
    memset(dis,0x3f3f3f,sizeof(dis));

    for (int i=1;i<=n;i++) dis[i][i]=0;

    for (int i=0;i<a.size();i++) dis[a[i]][b[i]]=dis[b[i]][a[i]]=len[i];

        for (int k=1;k<=n;k++)
        for (int i=1;i<=n;i++)
        for (int j=1;j<=n;j++)
        dis[i][j]=min(dis[i][j],dis[i][k]+dis[k][j]);

        int Max=1;
        for (int i=1;i<(1<<n);i++)
        {
            vector<int> V;
            V.clear();
            for (int j=0;j<n;j++)
            if (((i>>j)&1)==1) V.push_back(j+1);

            int m=V.size();
            int same=dis[V[0]][V[m-1]];
            int flag=1;

            for (int k=0;k<m;k++)
                for (int j=0;j<m;j++)
                if (k!=j&&dis[V[k]][V[j]]!=same)
                {
                flag=0;
                break;
            }
           if (flag) Max=max(Max,m);
        }
        return Max;
    }
};

C:很锻炼思维的题目。

参考他人的做法:

用类似后缀数组的方式。

只是数组套数组真心醉了。

我的方案是求出满足跟S一样序号的最小的字符串,然后比较与S的值.

代码中有详细注释。

#include<iostream>
#include <string>
#include <vector>
#include<string.h>
#include<algorithm>
using namespace std;
class SuffixArrayDiv2 {
     public:
     string  arr[100];
     int p[100],a[100];
     //注意P:表示字符串排完序后,所对应原来数组的下标
     //    A:表示原先字符串在排序后的下标
     // 这里很绕,熟悉后缀数组的应该了解
     char c[100];
     string smallerOne(string s) {
     for (int i=0;i<s.size();i++)
     arr[i]=&s[i];//保存后缀
     sort(arr,arr+s.size());

     int len=s.size();
     for (int i=0;i<s.size();i++){
          p[i]=len-arr[i].size();
          a[len-arr[i].size()]=i;
          }
          a[len]=-1;
          c[p[0]]=‘a‘;
     for (int i=1;i<len;i++){
          if (a[p[i-1]+1]<a[p[i]+1]) c[p[i]]=c[p[i-1]];
          //这个表示:我们确定位置为p[i]的字符,
          //如果当前字符串s1,与后面的字符串s2(都是排序后的字符串)
          //比较它们后面+1的字符串的大小。这里可以忽视我的解释
          else c[p[i]]=c[p[i-1]]+1;
    }
    string ans;
    for (int i=0;i<len;i++) ans+=c[i];
    if (ans<s) return "Exists";
    else return "Does not exist";

    }
};

int main()
{
   SuffixArrayDiv2 b;
   string s;
   cin>>s;
   cout<<b.smallerOne(s);
   return 0;
}
时间: 2024-10-09 12:53:56

Topcoder SRM 630div 2的相关文章

TopCoder SRM 625 Incrementing Sequence 题解

本题就是给出一个数k和一个数组,包括N个元素,通过每次增加数组中的一个数的操作,最后需要得到1 - N的一个序列,不用排序. 可以从暴力法入手,然后优化. 这里利用hash表进行优化,最终得到时间效率是O(n*n)的算法,而且常数项应该很低,速度还挺快的. 思路: 1 如果数组A[i]在1 -N 范围内,就利用bool B[]记录,这个数已经找到了: 2 如果A[i]的值之前已经找到了,那么就增加k操作,得到新的值A[i]+k,看这个值是否找到了,如果没找到,就使用B记录,如果之前已经找到了,那

Topcoder SRM 643 Div1 250&lt;peter_pan&gt;

Topcoder SRM 643 Div1 250 Problem 给一个整数N,再给一个vector<long long>v; N可以表示成若干个素数的乘积,N=p0*p1*p2*......*pn,我们假设p0,p1,...,pn是单调不降的,那么v里存储的是下标为偶数 的N的质因数p0,p2,p4,...,p(2k).现在要求写一个程序,返回一个vector<long long>ans; ans里存储的是p0,p1,p2,...,pn. Limits Time Limit(m

TopCoder SRM 634 Div.2[ABC]

TopCoder SRM 634 Div.2[ABC] ACM 题目地址: TopCoder SRM 634 赛后做的,感觉现场肯定做不出来Orz,简直不能多说. Level One-MountainRanges[水题] 题意: 问序列中有几个完全大于旁边的峰. 分析: 傻逼题,不多说. 代码: /* * Author: illuz <iilluzen[at]gmail.com> * File: one.cpp * Create Date: 2014-09-26 21:01:23 * Desc

TopCoder SRM 628 DIV 2

250-point problem Problem Statement    Janusz is learning how to play chess. He is using the standard chessboard with 8 rows and 8 columns. Both the rows and the columns are numbered 0 through 7. Thus, we can describe each cell using its two coordina

topcoder SRM 618 DIV2 WritingWords

只需要对word遍历一遍即可 int write(string word) { int cnt = 0; for(int i = 0 ; i < word.length(); ++ i){ cnt+=word[i]-'A'+1; } return cnt; } topcoder SRM 618 DIV2 WritingWords,布布扣,bubuko.com

topcoder SRM 618 DIV2 MovingRooksDiv2

一开始Y1,Y2两个参数看不懂,再看一遍题目后才知道,vector<int>索引代表是行数,值代表的是列 此题数据量不大,直接深度搜索即可 注意这里深度搜索的访问标识不是以前的索引和元素,而是一个交换元素后的整个状态vector<int>,这样可以避免重复元素的搜索 set<vector<int> > visit; bool flag; void dfs(vector<int>& src, vector<int>& d

topcoder SRM 618 DIV2 LongWordsDiv2

此题给出的条件是: (1)word的每个字母都是大写字母(此条件可以忽略,题目给的输入都是大写字母) (2) 相等字符不能连续,即不能出现AABC的连续相同的情况 (3)word中不存在字母组成xyxy的形式,即不存在第一个字符和第3个字符相等同时第2个字符和第4个字符相等的情况 对于第(2)种情况,只需要考虑word[i]!=word[i-1]即可 对于第(3)种情况,用一个4重循环遍历每种可能的情况,然后第一个字符和第3个字符相等同时第2个字符和第4个字符相等,则输出“DisLikes”即可

TOPCODER SRM 686 div2 1000

// TOPCODER SRM 686 div2 1000 Problem Statement 给出一个至多长 100 的字符串,仅包含 ( 和 ),问其中有多少个不重复的,合法的括号子序列. 子序列可以不连续:合法即括号序列的合法:答案模 1,000,000,007. Examples "(())(" Returns: 2 Correct non-empty bracket subsequences are "()" and "(())". &

topcoder srm 628 div2 250 500

做了一道题,对了,但是还是掉分了. 第二道题也做了,但是没有交上,不知道对错. 后来交上以后发现少判断了一个条件,改过之后就对了. 第一道题爆搜的,有点麻烦了,其实几行代码就行. 250贴代码: 1 #include <iostream> 2 #include <cstring> 3 #include <queue> 4 #include <cmath> 5 #include <cstdio> 6 #include <algorithm&g