[acwing周赛复盘] 第 113 场周赛20230722

总结

  • 又是笨比的一周,只做出1题。
  • T1 取模模拟
  • T2 字符串模拟
  • T3 组合数学
  • 在这里插入图片描述

5053. abc

链接: 5053. abc

1. 题目描述

在这里插入图片描述

2. 思路分析

  • 循环节是3,那么计算除3的商和余数即可模拟。

3. 代码实现

def solve():
    n, = RI()
    a,b = divmod(n,3)
    # print(a,b)
    ans = 'abc'*a
    if b ==1:
        ans += 'a'
    elif b == 2:
        ans += 'ab'
    print(ans)

5054. 拼接字符串

链接: 5054. 拼接字符串

1. 题目描述

在这里插入图片描述

2. 思路分析

  • 题目看着吓人,其实抛去特殊字符,就是判断一个set即可。
  • 把三个字符串所有组合情况放进set里,对询问直接in即可。

3. 代码实现

def solve():
    s1, = RS()
    s2, = RS()
    s3, = RS()
    ss = [s1.lower(), s2.lower(), s3.lower()]
    st = set()
    for x, y, z in permutations(ss):
        s = [c for c in x + y + z if c.isalpha()]
        st.add(''.join(s))

    n, = RI()
    for _ in range(n):
        q, = RS()
        s = [c.lower() for c in q if c.isalpha()]
        if ''.join(s) in st:
            print('ACC')
        else:
            print('WA')

5055. 画矩形

链接: 5055. 画矩形

1. 题目描述

在这里插入图片描述

2. 思路分析

先写了个dp,1000^5的记忆化搜索,而且不知道怎么优化。
  • 这时一般就得想数学了,尤其是方案数,很有可能是组合数学。
  • 发现其实是在内部n-1条横边画k个矩形,那么是选k*2条线,作为矩形的上下边。
  • 竖线同理。
  • 根据乘法原理,ans=C(n-1,k*2)C(m-1,k2)

  • cf2000分原题。

3. 代码实现

# Problem: 画矩形
# Contest: AcWing
# URL: https://www.acwing.com/problem/content/5058/
# Memory Limit: 256 MB
# Time Limit: 1000 ms

import sys
import random
from types import GeneratorType
import bisect
import io, os
from bisect import *
from collections import *
from contextlib import redirect_stdout
from itertools import *
from array import *
from functools import lru_cache, reduce
from heapq import *
from math import sqrt, gcd, inf

if sys.version >= '3.8':  # ACW没有comb
    from math import comb

RI = lambda: map(int, sys.stdin.buffer.readline().split())
RS = lambda: map(bytes.decode, sys.stdin.buffer.readline().strip().split())
RILST = lambda: list(RI())
DEBUG = lambda *x: sys.stderr.write(f'{str(x)}\n')
# print = lambda d: sys.stdout.write(str(d) + "\n")  # 打开可以快写,但是无法使用print(*ans,sep=' ')这种语法,需要print(' '.join(map(str, p))),确实会快。

DIRS = [(0, 1), (1, 0), (0, -1), (-1, 0)]  # 右下左上
DIRS8 = [(0, 1), (1, 1), (1, 0), (1, -1), (0, -1), (-1, -1), (-1, 0),
         (-1, 1)]  # →↘↓↙←↖↑↗
RANDOM = random.randrange(2 ** 62)
MOD = 10 ** 9 + 7
# MOD = 998244353
PROBLEM = """cf 2000分原题
https://codeforces.com/contest/128/problem/C
"""

class ModComb:
    """通过O(n)预处理逆元,达到O(1)询问组合数"""

    def __init__(self, n, p):
        """
        初始化,为了防止模不一样,因此不写默认值,强制要求调用者明示
        :param n:最大值
        :param p: 模
        """
        self.p = p
        self.inv_f, self.fact = [1] * (n + 1), [1] * (n + 1)
        inv_f, fact = self.inv_f, self.fact
        for i in range(2, n + 1):
            fact[i] = i * fact[i - 1] % p
        inv_f[-1] = pow(fact[-1], p - 2, p)
        for i in range(n, 0, -1):
            inv_f[i - 1] = i * inv_f[i] % p

    def comb(self, m, r):
        if m < r or r < 0:
            return 0
        return self.fact[m] * self.inv_f[r] % self.p * self.inv_f[m - r] % self.p

    def perm_count_with_duplicate(self, a):
        """含重复元素的列表a,全排列的种类。
        假设长度n,含x种元素,分别计数为[c1,c2,c3..cx]
        则答案是C(n,c1)*C(n-c1,c2)*C(n-c1-c2,c3)*...*C(cx,cx)
        或:n!/c1!/c2!/c3!/../cn!
        """
        ans = self.fact[len(a)]
        for c in Counter(a).values():
            ans = ans * self.inv_f[c] % self.p
        return ans
        # 下边这种也可以
        # s = len(a)
        # ans = 1
        # for c in Counter(a).values():
        #     ans = ans * self.comb(s,c) % MOD
        #     s -= c
        # return ans


#       ms
def solve():
    n, m, k = RI()
    mc = ModComb(1005, MOD)

    print(mc.comb(n - 1, k * 2) * mc.comb(m - 1, k * 2) % MOD)


if __name__ == '__main__':
    t = 0
    if t:
        t, = RI()
        for _ in range(t):
            solve()
    else:
        solve()

六、参考链接

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值