【上海交大oj】小M家的奶牛(回文字符串)

1066. 小M家的牛们

Description

小M是一位远近闻名的庄园主。因为近来牛肉涨价,精明小M决定开始养牛。为了方便跟踪所有的牛,小M在庄园上装了一套自动系统。他给了每一个头牛一个电子牌号。当牛走过这个系统时,牛的名字将被自动读入。

每一头牛的电子名字是一个长度为M的,由N个不同小写字母构成的字符串。

很快,淘气的牛找到了系统的漏洞:它们可以倒着走过读码器。一头名字为abcba不会导致任何问题,但是名为abcb的牛会变成两头牛(abcb和bcba)。

于是乎小M决定给牛们改名字,使得牛的名字正读和反读都一样。小M可以在任意位置添加或删除字母。但是,添加和删除每一个字母都有一定的费用。对于一个牛的名字和所有添加或删除字母的费用,找出修改名字的最小的费用。

注意:空字符串也是一个合法的名字。

Input Format

第一行:两个用空格分开的数,N和M。

第二行:M个字符,初始的牛的名字。

第3到N+2行:每行含有一个字母和两个整数,分别是添加和删除这个字母的费用。

0≤N≤26,0≤M≤2000 , 0≤费用≤10000

Output Format

一个整数,改变所有名字的最小费用。

Sample Input

3 4
abcb
a 1000 1100
b 350 700
c 200 800

Sample Output

900==========================================================================================================开始用的就是简单的递归算法,然后没有通过,最终用动态规划解决了。思想就是从两边开始遍历字符串,通过比较确定添加或删除哪边的字符。代码如下:

 1 //小M家的奶牛
 2 #include <iostream>
 3 #include <string>
 4 #include <vector>
 5 using namespace std;
 6
 7
 8 int clist[26];
 9 vector<vector<int> >state;  // 动态规划,记录状态
10 string ori_name;
11 int N,M;
12 int CalCost(int,int);
13 int main(){
14
15     cin>>N>>M>>ori_name;
16     state.resize(M);
17     for (int i=0;i<M;++i) state.at(i).resize(M,-1);
18
19     for (int i=0;i<N;++i) {
20         int acost,dcost;
21         char cha;
22         cin>>cha>>acost>>dcost;
23         clist[cha-‘a‘] = acost<dcost ? acost:dcost;
24     }
25     int min_cost = CalCost(0,M-1);
26     cout<<min_cost;
27
28     return 0;
29 }
30 int CalCost(int l,int r) {
31     int i,tem_cost1,tem_cost2;
32     char left,right;
33
34     if (l>=r) return 0;
35     if (ori_name[l]==ori_name[r]) return CalCost(++l,--r);
36     if (state.at(l).at(r)>=0) return state.at(l).at(r);
37     left = ori_name[l] - ‘a‘;
38     right = ori_name[r] - ‘a‘;
39     tem_cost1 = clist[left] + CalCost(l+1,r);
40     tem_cost2 = clist[right] + CalCost(l,r-1);
41     int min_cost = tem_cost1<tem_cost2 ? tem_cost1:tem_cost2;
42     state.at(l).at(r) = min_cost;
43     return min_cost;
44 }

 
时间: 2024-11-04 16:57:46

【上海交大oj】小M家的奶牛(回文字符串)的相关文章

nyist oj 37 回文字符串 (动态规划经典)

回文字符串 时间限制:3000 ms  |  内存限制:65535 KB 难度:4 描述 所谓回文字符串,就是一个字符串,从左到右读和从右到左读是完全一样的,比如"aba".当然,我们给你的问题不会再简单到判断一个字符串是不是回文字符串.现在要求你,给你一个字符串,可在任意位置添加字符,最少再添加几个字符,可以使这个字符串成为回文字符串. 输入 第一行给出整数N(0<N<100) 接下来的N行,每行一个字符串,每个字符串长度不超过1000. 输出 每行输出所需添加的最少字符

判断一个字符串是否为回文字符串

#include <stdio.h> #include <assert.h> #include <string.h> int is_pal_str(const char *p) {  assert(p);  int len = strlen(p);  const char *start = p;  const char *end = p+len - 1;  while (start < end)  {   if (*start == *end)   {    st

【LeetCode-面试算法经典-Java实现】【05-Longest Palindromic Substring(最大回文字符串)】

背景 近期開始研究算法,于是在leetcode上做算法题,第五题Longest Palindromic Substring便是关于回文子串的. 什么是回文字串 回文字符串是指将该字符串前后颠倒之后和该字符串一样的字符串.比如:a,aaaa,aba,abba- 最长回文子串 要求最长回文子串,就须要遍历每个子串,时间复杂度是O(N2):推断字串是不是回文,时间复杂度是O(N),这种话算法的时间复杂度就是O(N3). 我刚開始想到的就是中心扩展法,代码例如以下: public static Stri

判断是否是回文字符串(Java实现)

1.回文的定义:“回文数”就是正读倒读都一样的整数.如奇数个数字:98789,这个数字正读是98789 倒读也是98789.偶数个数字3223也是回文数.字母 abcba 也是回文. 2. 判断一个字符串是否是回文字符串(Java实现) 1 public class Test4 { 2 public static boolean isHuiWen(String text) { 3 int length = text.length(); 4 for (int i = 0; i < length /

shell脚本实现检测回文字符串

所有回文字的结构特征如下: 如果字符数是偶数,那么它在结构上表现为:一个字符序列连着另一个字符相同但次序恰好相反的字符序列. 如果字符数为奇数,那么它在结构上表现为:一个字符序列连着另一个字符相同但次序恰好相反的字符序列,但是这两个序列中间共享一个相同的字符. sed命令能够记住之前匹配的子样式.可以用正则表达式:'\(.\)',匹配任意一个字符,\1表示其反向引用.如匹配有两个字符的回文正则表达式为: '\(.\)\(.\)\2\1' 匹配任意长度的回文脚本如下所示: #!/bin/bash

最长回文字符串 POJ3974

曾经有一个好算法放到我面前,我没有好好珍惜,直到用到的时候才后悔莫及. 那就是Manacher(马拉车算法),以O(n)的复杂度计算最长回文字符串. 曾经刷Leetcode的时候,室友跟我说了这个算法,但当时那个题目用中间枚举也过了,我就没有在意,直到前天才弄会,写这篇报告之前, 我又专门写了一遍马拉车,果然还是有点问题的. 详细原理链接 点击 Mark #include <stdio.h> #include <iostream> #include <string.h>

Java Longest Palindromic Substring(最长回文字符串)

假设一个字符串从左向右写和从右向左写是一样的,这种字符串就叫做palindromic string.如aba,或者abba.本题是这种,给定输入一个字符串.要求输出一个子串,使得子串是最长的padromic string. 下边提供3种思路 1.两側比較法 以abba这样一个字符串为例来看,abba中,一共同拥有偶数个字.第1位=倒数第1位.第2位=倒数第2位......第N位=倒数第N位 以aba这样一个字符串为例来看,aba中.一共同拥有奇数个字符.排除掉正中间的那个字符后,第1位=倒数第1

131. 132. Palindrome Partitioning *HARD* -- 分割回文字符串

131. Palindrome Partitioning Given a string s, partition s such that every substring of the partition is a palindrome. Return all possible palindrome partitioning of s. For example, given s = "aab",Return [ ["aa","b"], ["

【又见LCS】NYOJ-37 回文字符串

[题目链接] 回文字符串 时间限制:3000 ms  |  内存限制:65535 KB 难度:4 描述 所谓回文字符串,就是一个字符串,从左到右读和从右到左读是完全一样的,比如"aba".当然,我们给你的问题不会再简单到判断一个字符串是不是回文字符串.现在要求你,给你一个字符串,可在任意位置添加字符,最少再添加几个字符,可以使这个字符串成为回文字符串. 输入 第一行给出整数N(0<N<100)接下来的N行,每行一个字符串,每个字符串长度不超过1000. 输出 每行输出所需添