题解 | #nico和niconiconi#

nico和niconiconi

http://www.nowcoder.com/practice/70a03345bae6499ea4338ebc3a0b60e9

描述

给定一个字符串 S ,定义三种有价值的字符串: A = "nico" ,B = "niconi" , C = "niconiconi"
其中,字符串 A 的价值为 a, 字符串 B 的价值为 b,字符串 C 的价值为 c
她拿到了一个长度为 n 的字符串,你需要在其中找到一些有价值的子串 (指字符串中连续的一段),并统计价值之和的最大值。
注:已被计算价值过的字符不能重复计算价值!如 "niconico" 要么当作 "nico" + "nico" 计 2a 分,要么当作 "niconi" + "co" 计 b 分(其中 "co" 不计分)。

示例1

输入:
19 1 2 5
niconiconiconiconi~

输出:
7

说明:
"niconi"co"niconiconi"~
故为2+5=7分

示例2

输入:
6 1 2 5
nocole

输出:
0

思路

开门见山了,这道题可以采用动态规划的方式来解决。
首先,状态转移方程是:

dp[i] = Math.max(dp[i], Math.max(dp[i-3]+a, dp[i-5]+b, dp[i-9]+c))

其实也不难理解,就是没到一个地方,就判断一下符合 a、b、c 那个,在取最大的就行,然后用 dp 数组记录一下,注意:dp 数组是递增或平行的。

AC 代码


import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        String line = sc.nextLine();
        String[] split = line.split(" ");
        int n = Integer.parseInt(split[0]);
        int a = Integer.parseInt(split[1]);
        int b = Integer.parseInt(split[2]);
        int c = Integer.parseInt(split[3]);
        String line1 = sc.nextLine();
        long res = run1(n, a, b, c, line1);
        System.out.println(res);
    }


    public static long run1(int n, int a, int b, int c, String s) {
        if (s == null || s.length() < 4) {
            return 0;
        }

        long[] dp = new long[n];

        for (int i = 3; i < n; i ++) {
            dp[i] = dp[i - 1];
            if (i >= 3 && s.substring(i- 3, i + 1).equals("nico")) {
                dp[i] = Math.max(dp[i], dp[i - 3] + a);
            }
            if (i >=5 && s.substring(i - 5, i + 1).equals("niconi")) {
                dp[i] = Math.max(dp[i], dp[i - 5] + b);
            }
            if (i >= 9 && s.substring(i - 9, i + 1).equals("niconiconi")) {
                dp[i] = Math.max(dp[i], dp[i - 9] + c);
            }
        }

        return dp[n - 1];
    }
}

  • 时间复杂度:O(N), N 为字符串长度,需要遍历一遍
  • 空间复杂度:O(N), N 为字符串长度,需要创建 dp 数组
AC_算法题 文章被收录于专栏

AC 算法题

全部评论

相关推荐

04-08 23:14
已编辑
南阳理工学院 算法工程师
本人情况:26届双非本科,两段实习经历,目前拿到的都是实习的offer,一个校招的都没有,他们都说先实习,然后等拿到毕业证了直接转正,我又害怕干三个月给我叉出去面试题也发一下吧###&nbsp;杭州问尔信息技术后端登录你是怎么做的?JWT令牌你了解过吗?他虽然是一段字符串,他表达了什么东西?怎么解析出来信息和过期时间?JWT令牌怎么续期?如果我拉黑一个账号,要怎么做?两种方案(有无redis)mongodb和mysql的区别?mongodb和mysql分别实用于什么项目?选型你会怎么选?数据库的事务,那些地方需要使用,那些地方不需要使用?他会影响什么性能?mysql和pgsql有什么差异你知道吗?消息队列&nbsp;redis也有,为什么要用mq?前后端会部署吗?docker会用吗?内部通信前端&nbsp;async和&nbsp;await你知道吗?异步编程的原理是什么?vue3&nbsp;为什么你改变一个字符串&nbsp;前端会跟着改动AI工具会用什么?你会怎么用?###&nbsp;仲财通常用的锁有哪些synchronize和ReentrantLock的区别分布式锁了解吗?分布式事务mysql表字段sql优化什么时候用索引索引什么时候会失效mysql事务ioc一些项目应用问题###&nbsp;观妙科技项目问题...zset的架构是什么样子的线程池突然队列被打满了怎么办?如果上游和下游都无法控制,该怎么维护select&nbsp;*&nbsp;from&nbsp;user&nbsp;where&nbsp;age&gt;20&nbsp;order&nbsp;by&nbsp;update_time&nbsp;索引设计检索过程是什么样的冒泡排序和快排,有什么区别怎么判断链表有没有环###&nbsp;观妙科技-二面项目部分...线程池的核心参数有哪些你是怎么用线程池的JMMG1模型跳表介绍一下平衡二叉树TCP为什么要三次握手?说一下hashmap红黑树的特征你有什么学习的方法
牛马人的牛马人生:对学院本而言很强了
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务