首页 > 其他分享 >2023-06-28:你想要用小写字母组成一个目标字符串 target。 开始的时候,序列由 target.length 个 ‘?‘ 记号组成 而你有一个小写字母印章 stamp。 在每个回合,你可

2023-06-28:你想要用小写字母组成一个目标字符串 target。 开始的时候,序列由 target.length 个 ‘?‘ 记号组成 而你有一个小写字母印章 stamp。 在每个回合,你可

时间:2023-06-28 20:34:01浏览次数:65  
标签:06 target 小写字母 stamp 印章 let path cur

2023-06-28:你想要用小写字母组成一个目标字符串 target。

开始的时候,序列由 target.length 个 '?' 记号组成

而你有一个小写字母印章 stamp。

在每个回合,你可以将印章放在序列上,并将序列中的每个字母替换为印章上的相应字母

你最多可以进行 10 * target.length 个回合

举个例子,如果初始序列为 "?????",而你的印章 stamp 是 "abc"

那么在第一回合,你可以得到 "abc??"、"?abc?"、"??abc"

(请注意,印章必须完全包含在序列的边界内才能盖下去。)

如果可以印出序列,那么返回一个数组,该数组由每个回合中被印下的最左边字母的索引组成

如果不能印出序列,就返回一个空数组。

例如,如果序列是 "ababc",印章是 "abc"

那么我们就可以返回与操作 "?????" -> "abc??" -> "ababc" 相对应的答案 [0, 2]

另外,如果可以印出序列,那么需要保证可以在 10 * target.length 个回合内完成

任何超过此数字的答案将不被接受。

输入:stamp = "abc", target = "ababc"。

输出:[0,2]。

答案2023-06-28:

大体步骤如下:

1.创建变量s和t,分别存储印章stamp和目标字符串target的字节数组表示。

2.创建变量m和n,分别存储印章长度和目标字符串长度。

3.创建数组inDegrees,长度为n-m+1,初始化每个元素为m。该数组表示每个位置需要匹配的印章字符数量。

4.创建二维数组graph,长度为n,每个位置是一个空的整数数组。该数组表示目标字符串每个位置对应的可能的匹配位置。

5.创建队列queue,长度为n-m+1,用于存储已经匹配完所有印章字符的位置。

6.创建变量l和r,分别表示队列queue的左右指针,初始时都为0。

7.遍历目标字符串,从0到n-m,依次处理每个位置:

7.1.在当前位置i,遍历印章的每个字符:

7.1.1.若目标字符串t的第i+j个字符与印章字符相等,表示匹配成功,更新inDegrees数组,将对应位置的值减1。

7.1.1.1.如果经过减1操作后,该位置上印章字符匹配数量变为0,将该位置加入队列queue,并将右指针r向右移动。

7.1.2. 若目标字符串t的第i+j个字符与印章字符不相等,表示匹配失败,将该位置加入graph[i+j]数组中,表示可以在该位置之后的某个位置尝试匹配印章。

8.创建bool类型的数组visited,长度为n,用于标记目标字符串的位置是否被访问过。

9.创建数组path,长度为n-m+1,用于记录完成印章替换的顺序。

10.创建变量size,初始为0,表示已经完成替换的印章的数量。

11.当左指针l小于右指针r时,执行以下循环:

11.1.取出队列queue中的当前位置cur,并将左指针l右移。

11.2.将当前位置cur加入数组path中,并增加size的值。

11.3.遍历印章的每个字符:

11.3.1.若当前位置cur+i未被访问过,表示可以尝试在该位置继续匹配印章:

11.3.1.1.将该位置标记为已访问visited[cur+i] = true。

11.3.1.2.遍历当前位置cur+i对应的graph数组中的每个位置next:

11.3.1.2.1.更新inDegrees数组,将对应位置的值减1。

11.3.1.2.1.1.如果经过减1操作后,该位置上印章字符匹配数量变为0,将该位置加入队列queue,并将右指针r向右移动。

12.检查完成替换的印章数量是否等于n-m+1,如果不相等,返回空数组[]。

13.将数组path中的元素按照首尾对称的顺序重新排列,即交换元素path[i]和path[j],其中i从0遍历到size-1,j从size-1遍历到0。

14.返回数组path作为结果。

该程序的总时间复杂度和总空间复杂度为:

总时间复杂度:O((n - m + 1) * m),其中n是target字符串的长度,m是stamp字符串的长度。

总空间复杂度:O(n),其中n是target字符串的长度。

go完整代码如下:

package main

import (
	"fmt"
)

func movesToStamp(stamp string, target string) []int {
	s := []byte(stamp)
	t := []byte(target)
	m := len(s)
	n := len(t)
	inDegrees := make([]int, n-m+1)
	for i := range inDegrees {
		inDegrees[i] = m
	}
	graph := make([][]int, n)
	for i := range graph {
		graph[i] = []int{}
	}
	queue := make([]int, n-m+1)
	l, r := 0, 0
	for i := 0; i <= n-m; i++ {
		for j := 0; j < m; j++ {
			if t[i+j] == s[j] {
				if inDegrees[i]--; inDegrees[i] == 0 {
					queue[r] = i
					r++
				}
			} else {
				graph[i+j] = append(graph[i+j], i)
			}
		}
	}
	visited := make([]bool, n)
	path := make([]int, n-m+1)
	size := 0
	for l < r {
		cur := queue[l]
		l++
		path[size] = cur
		size++
		for i := 0; i < m; i++ {
			if !visited[cur+i] {
				visited[cur+i] = true
				for _, next := range graph[cur+i] {
					if inDegrees[next]--; inDegrees[next] == 0 {
						queue[r] = next
						r++
					}
				}
			}
		}
	}
	if size != n-m+1 {
		return []int{}
	}
	for i, j := 0, size-1; i < j; i, j = i+1, j-1 {
		path[i], path[j] = path[j], path[i]
	}
	return path
}

func main() {
	stamp := "abc"
	target := "ababc"
	result := movesToStamp(stamp, target)
	fmt.Println(result)
}

在这里插入图片描述

rust完整代码如下:

fn moves_to_stamp(stamp: String, target: String) -> Vec<i32> {
    let s: Vec<char> = stamp.chars().collect();
    let t: Vec<char> = target.chars().collect();
    let m = s.len();
    let n = t.len();
    let mut in_degrees: Vec<i32> = vec![m as i32; n - m + 1];
    let mut graph: Vec<Vec<i32>> = vec![Vec::new(); n];
    let mut queue: Vec<i32> = vec![0; n - m + 1];
    let mut l = 0;
    let mut r = 0;

    for i in 0..=n - m {
        for j in 0..m {
            if t[i + j] == s[j] {
                if in_degrees[i] > 0 {
                    in_degrees[i] -= 1;
                }

                if in_degrees[i] == 0 {
                    queue[r] = i as i32;
                    r += 1;
                }
            } else {
                graph[i + j].push(i as i32);
            }
        }
    }

    let mut visited: Vec<bool> = vec![false; n];
    let mut path: Vec<i32> = vec![0; n - m + 1];
    let mut size = 0;

    while l < r {
        let cur = queue[l];
        l += 1;
        path[size] = cur;
        size += 1;

        for i in 0..m {
            let cur_i = cur + i as i32;
            if !visited[cur_i as usize] {
                visited[cur_i as usize] = true;
                for &next in &graph[cur_i as usize] {
                    if in_degrees[next as usize] > 0 {
                        in_degrees[next as usize] -= 1;
                    }

                    if in_degrees[next as usize] == 0 {
                        queue[r] = next;
                        r += 1;
                    }
                }
            }
        }
    }

    if size != n - m + 1 {
        return Vec::new();
    }

    for i in 0..size / 2 {
        let tmp = path[i];
        path[i] = path[size - 1 - i];
        path[size - 1 - i] = tmp;
    }

    path
}

fn main() {
    let stamp = String::from("abc");
    let target = String::from("ababc");
    let result = moves_to_stamp(stamp, target);
    println!("{:?}", result);
}

在这里插入图片描述

c++完整代码如下:

#include <iostream>
#include <vector>
#include <algorithm>

using namespace std;

vector<int> movesToStamp(string stamp, string target) {
    int m = stamp.length();
    int n = target.length();
    vector<int> inDegrees(n - m + 1, m);
    vector<vector<int>> graph(n, vector<int>());
    vector<int> queue(n - m + 1, 0);
    int l = 0, r = 0;

    for (int i = 0; i <= n - m; i++) {
        for (int j = 0; j < m; j++) {
            if (target[i + j] == stamp[j]) {
                if (--inDegrees[i] == 0) {
                    queue[r++] = i;
                }
            }
            else {
                graph[i + j].push_back(i);
            }
        }
    }

    vector<bool> visited(n, false);
    vector<int> path(n - m + 1, 0);
    int size = 0;

    while (l < r) {
        int cur = queue[l++];
        path[size++] = cur;

        for (int i = 0; i < m; i++) {
            if (!visited[cur + i]) {
                visited[cur + i] = true;

                for (int next : graph[cur + i]) {
                    if (--inDegrees[next] == 0) {
                        queue[r++] = next;
                    }
                }
            }
        }
    }

    if (size != n - m + 1) {
        return vector<int>();
    }

    reverse(path.begin(), path.begin() + size);
    return path;
}

int main() {
    string stamp = "abc";
    string target = "ababc";

    vector<int> result = movesToStamp(stamp, target);

    cout << "Result: ";
    for (int num : result) {
        cout << num << " ";
    }
    cout << endl;

    return 0;
}

在这里插入图片描述

标签:06,target,小写字母,stamp,印章,let,path,cur
From: https://www.cnblogs.com/moonfdd/p/17512486.html

相关文章

  • 2023-06-28:你想要用小写字母组成一个目标字符串 target。 开始的时候,序列由 target.le
    2023-06-28:你想要用小写字母组成一个目标字符串target。开始的时候,序列由target.length个'?'记号组成而你有一个小写字母印章stamp。在每个回合,你可以将印章放在序列上,并将序列中的每个字母替换为印章上的相应字母你最多可以进行10*target.length个回合举个例子,如果初始......
  • 欧奈儿行业 RPS 排名,一图览全貌 2023-06-28,汽车零部件进入跟踪视野
    自动复盘2023-06-28k线图是最好的老师,点击详情图可以看到行业20日RPS的排名,最底下子图是行业rps走势线跟踪板块总结:成交额超过100亿排名靠前,macd柱由绿转红成交量要大于均线有必要给每个行业加一个上级的归类,这样更能体现主流方向rps有时候比较滞后,但不少是欲......
  • 2023-06-28《计算方法》- 陈丽娟 - 向量和矩阵基础.md
    2023-06-28《计算方法》-陈丽娟-向量和矩阵基础Matlab计算方法矩阵范数导数条件数本问补充向量和矩阵范数的相关知识,为下一章节的线性方程组的迭代法以及误差分析做准备。除了参考《计算方法》一书,还参考了华东师范大学数学学院的课程材料《迭代方法与预处理》以及陈新宇、伍......
  • 2023-06-28 小程序、h5、App各端的条件编译
    //表示代码仅在H5平台上面执行,其他平台不执行<!--#ifdefH5-->需条件编译的代码<!--#endif-->//表示代码在H5平台上面不执行,其他平台上面执行<!--#ifndefH5-->需条件编译的代码<!--#endif-->//表示代码在H5平台和App......
  • 20230628
    最近忙了三四个的准备去参展的项目被取消了,领导没有正面通知,听负责采购的同事说的,采购关于展会用的物料被拒批,忙了几个月,突然一下松了下来来,这几天基本上都是摸摸鱼,工作状态一下一下子,松懈了下来。今天看到一个博客园的哥们的在博客园上分享了近十年的经历,感觉挺有意思的,我关注了......
  • 20230628水题选做
    约束条件题意给定一些关系\(x=y或x\neqy\)。求是否能满足。分析显然并查集。我们考虑将约束条件排序,先使形如\(x_{i}=x_{j}\)的\(x_{i}\)和\(x_{j}\)合并。而后我们观察是否存在\(x_{i}\)和\(x_{j}\)已经合并但是关系是\(\neq\)。代码#include<bits/stdc++.h>usingname......
  • C/C++自助点餐系统[2023-06-28]
    C/C++自助点餐系统[2023-06-28]面向对象程序课程设计任务书【题目】自助点餐系统【目的】通过设计一个小型的自助点餐系统,训练综合运用所学知识处理实际问题的能力,强化面向对象的程序设计理念,使自己的程序设计与调试水平有一个明显的提高。【要求】1、每个学生必须独立完成;......
  • AtCoder Beginner Contest 306(ABC 306) E~F补题
    E题目大意给定数字$k$,规定数组$A$的函数$f(A)$:$A$数组前$k$大数字的和如$A=[1,3,7,~4]$,$k=2$,则$f(A)=7+4=11$现在给定最大数组长度$n$,有$q$组操作,每次将第$x$个数字修改为$y$,输出每次操作后的$f(A)$其中$0<k\leqn\leq5\times10^5,~q\leq5\times......
  • .NET周报 【6月第4期 2023-06-25】
    国内文章如何在long-runningtask中调用async方法https://www.cnblogs.com/eventhorizon/p/17497359.htmllong-runningtask是指那些长时间运行的任务,比如在一个whileTrue中执行耗时较长的同步处理。本文带你了解在long-runningtask中调用async方法的姿势。使用C#进行A......
  • SummerResearch_Log_20230627
    WorkingContent:1.今天开始看VisionTransformer(ViT):看之前需要一些基础:(1)RNN(RecurrentNN,循环神经网络):一段连续的信息,前后信息之间是有关系地,必须将不同时刻的信息放在一起理解。如果是普通的神经网络,每个输入之间是相互独立的,如果是RNN,则可以接收上一个输入传递的信息。......