String 返回在两个给定字符串之间排序的新字符串
给定两个字符串a和b,其中a在字典上String 返回在两个给定字符串之间排序的新字符串,string,algorithm,sorting,String,Algorithm,Sorting,给定两个字符串a和b,其中a在字典上abcf abc~abchi->abc+\uh->abc 连续字符 如果两个不同的字符按字典顺序连续,请首先复制左字符,然后在左字符串的下一个字符和字母表末尾之间添加字符: abhs~abit->ab+h~i->abh+s~(->abhw abh~abit->ab+h~i->abh+~\uUh->abhn 如果左字符串中的下一个字符是一个或多个z,则复制它们并在第一个非z字符和字母表末尾之间添加字符: abhz~abit->ab+h~i->abh+z~┱-
有一个实用的算法吗?这是一个非常简单的方法来实现这一点,可能远远不是最优的(当然取决于你所说的最优) 我只使用
a
和b
。我想你可以用更多的字母来概括这一点
两个简单的观察结果:
abba
<abba
x
以b
结尾时,才能保证在另一个字符串x
之前创建一个新字符串。现在,用a
替换b
,并附加一个或多个字母。例如,abbab
abbaab
算法现在非常简单。以
a
和b
作为哨兵开始。在两个现有钥匙x
和y
之间插入新钥匙:
- 如果
是x
的前缀:新键是y
,其结尾y
替换为b
ab
- 如果
不是x
的前缀:新键是y
,附加了x
b
运行示例:
a, b
a, ab*, b
a, aab*, ab, b
a, aab, ab, abb*, b
a, aab, ab, abab*, abb, b
a, aaab*, aab, ab, abab, abb, b
最小化字符串长度 如果希望将字符串长度保持在最小值,可以创建一个在左右字符串之间按字典顺序排列的字符串,以便有空间插入其他字符串,并且仅在绝对必要时创建更长的字符串 我将假设字母表[a-z]和字典顺序,其中空格位于“a”之前,因此例如“ab”位于“abc”之前 基本情况 首先从字符串的开头复制字符,直到遇到第一个差异(可能是两个不同的字符,也可能是左字符串的结尾):
abcde~abchi->abc+d~h
abc~abchi->abc+\uh
然后,通过在字母表中左字符(或字母表的开头)和右字符之间的中间添加字符来创建新字符串:
abcde~abchi->abc+d~h->abcf
abc~abchi->abc+\uh->abc
连续字符
如果两个不同的字符按字典顺序连续,请首先复制左字符,然后在左字符串的下一个字符和字母表末尾之间添加字符:
abhs~abit->ab+h~i->abh+s~(->abhw
abh~abit->ab+h~i->abh+~\uUh->abhn
如果左字符串中的下一个字符是一个或多个z,则复制它们并在第一个非z字符和字母表末尾之间添加字符:
abhz~abit->ab+h~i->abh+z~┱->abhz+┱~┱->abhzn
abhzs~abit->ab+h~i->abh+z~ u->abhz+s~ u->abhzw
abhzz~abit->ab+h~i->abh+z~->…->abhzz+u~ uz->abhzzn
右边的字符是a或b
永远不要在左字符串后面加上“a”来创建字符串,因为这样会创建两个按字典顺序连续的字符串,在这两个字符串之间不能再添加其他字符串。解决方案是始终在字母表开头和右字符串中的下一个字符之间添加一个附加字符:
abc~abcah->abc+\ua->abca+\uh->abcad
abc~abcab->abc+\ua->abca+\ub->abcaa+\uu->abcaan
abc~abcaah->abc+\uA->abca+\uA->abcaa+\uH->abcaad
abc~abcb->abc+\ub->abca+\uuu->abcan
代码示例
下面是演示该方法的代码片段。这有点复杂,因为JavaScript,但实际上并不复杂。要生成第一个字符串,请使用两个空字符串调用函数;这将生成字符串“n”。要在最左边的字符串之前或最右边的字符串之后插入字符串,请使用该字符串和空字符串调用函数
功能中间串(上一个,下一个){
变量p,n,pos,str;
对于(pos=0;p==n;pos++){//查找最左边的不匹配字符
p=pos"strings": [
"n",
"u",
"x",
"z",
"zn",
"zu",
"zx",
"zz",
"zzn",
"zzu",
"zzx",
"zzz",
"zzzn",
"zzzu",
"zzzx",
"zzzz",
"...etc...",
"zzzzzzzzzzzzzzzzzzzzzzzzn",
"zzzzzzzzzzzzzzzzzzzzzzzzu",
"zzzzzzzzzzzzzzzzzzzzzzzzx",
"zzzzzzzzzzzzzzzzzzzzzzzzz",
"zzzzzzzzzzzzzzzzzzzzzzzzzn"
]
// Copyright 2021 Google LLC.
// SPDX-License-Identifier: Apache-2.0
template <typename Str, typename Digit>
Str midpoint(const Str left, const Str right, Digit zero, Digit nine) {
Str mid;
for (auto i = left.size() - left.size();; ++i) {
Digit l = i < left.size() ? left[i] : zero;
Digit r = i < right.size() ? right[i] : nine;
if (i == right.size() - 1) --r;
// This is mid += (l + r + 1)/2
// without needing Digit to be wider than nine.
r -= l;
mid += l + r/2 + (r&1);
if (mid.back() != l) break;
}
return mid;
}