检查字符串是否完全由相同的子字符串组成


24

这是从这个问题中获得的(当然需要允许)。我会引用:

创建一个接受字符串的函数,该函数应根据输入是否包含重复的字符序列来返回true或false 。给定字符串的长度始终大于1,并且字符序列必须至少重复一次。

一些例子:

'aa' //true
'aaa' //true
'abcabcabc' //true
'aba' //false
'ababa' //false
'weqweqweqweqweqw' // false

具体来说,检查严格由重复子字符串组成的字符串(Update)可以输出任何真或假表示,但请不要输出错误。严格的字母数字字符串。否则为标准代码高尔夫球规则。这是Code Golf,因此每种语言的最短答案(以字节为单位)获胜。


4
嗯,我打算以挑战者的身份结束这一挑战,但我注意到另一个挑战者在角色计数上得分很高。因此,也许我们应该关闭另一个(它也有一个可接受的答案),以代替对此的欺骗。
暴民埃里克

Answers:


11

Brachylog4 3个字节

ġ=Ṁ

在线尝试!

说明

ġ=Ṁ    Implicit input, say "abcabc"
ġ      Split into chunks of equal lengths (except maybe the last one): ["abc","abc"]
 =     Apply the constraint that all of the chunks are equal,
  Ṁ    and that there are multiple of them.

true.如果可以满足约束条件,则打印程序,如果不满足,false.则打印。


在我注意到一个小时前发布这个消息之前,我只是在努力尝试获得类似的东西~j↙=Ṁc工作
不相关的字符串

4
哦,是的,这可能要短一个字节:ġ=Ṁ
不相关的字符串

是一个约束为两个或多个元素的列表的变量)
不相关的字符串

1
@UnrelatedString很好,谢谢!我不认为要检查变量Wiki页面。
Zgarb

1
很多很棒的答案,而LUA答案在我心中占有特殊的位置。Arnauld的回答特别贴切,因为我基于此的原始问题(不是欺骗)实际上是标记为Javascript的。主要选择该语言仅仅是因为它似乎确实是所有语言中总体上最短的,而且,因为这是我的第一个问题,所以我得到了一个徽章。
ouflak

19

JavaScript(ES6),22个字节

返回一个布尔值。

s=>/^(.*)\1+$/.test(s)

在线尝试!


没有正则表达式, 33  29字节

返回null(虚假)或对象(真实)。

s=>(s+s).slice(1,-1).match(s)

在线尝试!

注意:从技术上讲,被转换为match()的正则表达式,因此上面的标题是一个谎言。s


9

grep,19岁

grep -qxE '(.+)\1+'

测试

while read; do 
  <<<"$REPLY" grep -qxE '(.+)\1+' && t="true" || t="false"
  echo "$REPLY: $t"
done < infile 

输出:

aa: true
aaa: true
abcabcabc: true
aba: false
ababa: false
weqweqweqweqweqw: false

9

Japt,6个字节

²é ¤øU

@Shaggy节省了一个字节

在线尝试!

        Implicit input, stored in variable 'U'
²       U+U, "abcabc" -> "abcabcabcabc"
 é      Rotate 1 char to the right "abcabcabcabc" -> "cabcabcabcab"
   ¤    Remove first two chars, "cabcabcabcab" -> "bcabcabcab"
    øU  Check if U is in the above

尼斯一个:)你可以替换p<space>使用²,以节省一个字节。
毛茸茸的


7

Excel,26个字节

=FIND(A1,A1&A1,2)<=LEN(A1)

来自A1的输入,输出到您放置此公式的任何单元格。


如果您定义了一个单字母范围名称(例如A)并将其设置为输入,则可以节省4个字节。
i_saw_drones

@i_saw_drones-我认为这是标准I / O规则所不允许的:这是指向适用于该方法的元答案的链接;目前票数为-36。
Sophia Lechner

抱歉,尽管考虑过,但我没有看到该帖子,A1因为它包含输入值,它也不是“变量”吗?:)
i_saw_drones

1
如果我对它特别是A1做任何特殊的事情,我会感觉像那样,就像我以某种方式依赖其ROW(_)为1一样。尽管如此,它只是提供带有任意输入。
索菲亚·莱希纳

7

R,28个字节

grepl("(.+)\\1+$",scan(,''))

在线尝试!

简单的Regex版本。R(有时)与Python非常相似,因此它与TFeld的Python 2正则表达式答案相似,尽管更短!

问题(如果有人知道答案)

我仍然感到困惑,为什么这样做有效,因为子字符串可以是任意长度,并且始终可以工作,而且当我在有效字符串的开头添加字母(例如“ cABABABABAB”)时仍然可以工作。如果我亲自阅读正则表达式,则会看到(.+),它捕获了任何长度的任何组。然后\\1+$,它将重复捕获的组多次直到结束。

那么,为什么它不只捕获“ AB”并发现它一直重复到字符串的末尾,特别是因为没有指定关于子字符串可以在何处开始的限制?


1
有趣的是,这似乎是R的regex引擎中的错误。perl=TRUE如您所料,添加选项使其与cABABAB匹配。grep -E '(.*)\1+$'即使grep -E使用ERE,使用bash 运行也可以匹配cABABAB,应该使用相同的regex风味R。
Grimmy

2
我的猜测是这是应用错误的优化。改变.+在一个模式的开始^.+是一个重要的优化,但如果.+是内捕获它的括号被停止有效。
Grimmy


6

果冻 5  4 字节

我现在知道,最佳方法是遵循xnor的方法

Ḋ;Ṗw

单子链接,它接受一个字符列表并输出一个整数-重复片段的最短长度;如果不存在,则为零。请注意,在Jelly中,零为假,而非零为真。

在线尝试!

怎么样?

Ḋ;Ṗw - Link: list of characters, S   e.g. "abcabcabc"   or "abababa"
Ḋ    - dequeue S                           "bcabcabc"       "bababa"
  Ṗ  - pop from S                         "abcabcab"       "ababab"
 ;   - concatenate                "bcabcabcabcabcab"       "bababaababab"
   w - first index of sublist     3  ^---here!             0  (not found)







3

C#(Visual C#交互式编译器),70字节

xnor的无耻改编(46字节

s=>(s+s).Substring(1,s.Length*2-2).Contains(s)

我的非Regex解决方案:

s=>s.Select((x,y)=>y).Count(z=>s.Replace(s.Substring(0,z+1),"")=="")>1

说明:

用空字符串替换从索引0开始的所有可能的子字符串。如果结果为空字符串,则该字符串完全由该子字符串组成。由于这包括评估整个字符串本身,因此预期结果的数量必须大于1。

示例:abcabc

从索引0开始的可能子字符串:

'a', 'ab', 'abc', 'abca', 'abcab', 'abcabc'

如果我们用空字符串替换它们

Substring          Result

'a'         =>     'bcbc'
'ab'        =>     'cc'
'abc'       =>     ''
'abca'      =>     'bc'
'abcab'     =>     'c'
'abcabc'    =>     ''

由于除了“ abcabc”以外,还有一个子字符串返回一个空字符串,因此该字符串完全由另一个子字符串(“ abc”)组成

在线尝试!


3

Python 3中62 60 56 54个字节

-4字节thanx到ArBo

lambda s:s in(len(s)//l*s[:l]for l in range(1,len(s)))
  1. 遍历字符串中所有可能的前缀。
  2. 尝试使用前缀构建字符串。
  3. 返回此操作是否以任何前缀成功完成。

在线尝试!


1
好答案!该f=可被丢弃; 通常允许使用匿名函数。同样,通过切换到Python 2并检查列表的成员身份而不是any构造,您可以获取55个字节
ArBo

1
会员列表,thanx很不错!我不会切换到Python 2,因为这就像切换语言一样,这显然不是重点;)另外,是否有一种方便的方法可以在TIO中测试匿名函数并保持字节数?
movatica

1
@movatica在标题中放入`f =`(\是python中的行继续符)
Artemis支持Monica

令人讨厌的是,\也是转义字符。在这里,无需代码格式化,应放在标题中:f = \
Artemis支持Monica

2

Japt,10字节

如果为true,则返回正数;如果为false,则返回0。如果要布尔输出,只需添加标志

å+ k@rXÃÊÉ

å+ k@rXÃÊÉ      Full program. Implicit input U.
                    e.g: U = "abcabcabc"
å+              Take all prefixes 
                         U = ["a","ab","abc","abca","abcab","abcabc","abcabca","abcabcab","abcabcabc"]
   k@           Filter U by:
     rXÃ        Values that return false (empty string)
                when replacing each prefix in U
                e.g: ["bcbcbc","ccc","","bcabc","cabc","abc","bc","c",""]
                                take ↑                             and ↑
                     U = ["abc","abcabcabc"]
         ÊÉ     Get U length and subtract 1. Then return the result

在线尝试!


2

外壳,6个字节

Ṡ€ȯhtD

在线尝试!

我觉得这比最优值多了一个字节,但是我找不到一种安排来进行明确的组合 ȯ不必要。

说明

Ṡ€      Find the argument in the result of applying the following function to the argument
  ȯhtD  Duplicate the argument, then remove the first and last elements.

2
€htD¹避免了ȯ
Zgarb

这太妙了!我曾考虑过,λ€htD¹但我没有意识到会隐式添加lambda
Sophia Lechner

2

Mathematica 11.x,74个字节

{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&

在整个图中,其中#表示输入字符串,并且

StringCases[#,<pattern>]

查找与模式匹配的输入字符串的子字符串

StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="") 

此模式需要匹配项,x必须从字符串的开头开始,并且必须满足以下条件:(1)匹配项不是整个输入字符串,以及(2)如果我们将输入字符串中匹配项的出现替换为空字符串我们获得空字符串。最后,将匹配列表与空白列表进行比较,

{}!=

True,如果匹配的列表不为空并且False如果匹配的列表是空的。

测试用例:

{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&["aa"]
(*  True  *)
{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&["aaa"]
(*  True  *)
{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&["abcabc"]
(*  True  *)

{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&["aba"]
(*  False  *)
{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&["ababa"]
(*  False  *)
{}!=StringCases[#,StartOfString~~x__/;(x!=#&&StringReplace[#,x->""]=="")]&["weqweqweqweqweqw"]
(*  False  *)

2

Python 3,84个字节

import textwrap
lambda s:any(len(set(textwrap.wrap(s,l)))<2 for l in range(1,len(s)))

使用textwrap.wrap(由于此答案)将字符串分成多个长度,n以测试重复子字符串的每个可能的长度。然后通过将拆分后的部分添加到集合中来将它们进行比较。如果所有片段均相等,并且集合长度为1,则字符串必须是重复字符串。我之所以用<2代替,是==1因为它节省了一个字节,并且保证了输入字符串的长度大于零。

如果没有n长度重复的子字符串n组成整个字符串,则对于整个函数返回false。


2

05AB1E,5个字节

上一个问题中的xnor方法在05AB1E中似乎也是最佳的。

«¦¨så

在线尝试! 或作为测试套件

说明

«       # append input to input
 ¦¨     # remove the first and last character of the resulting string
   så   # check if the input is in this string

1
当然..当我看到那里没有人时,我将要回答05AB1E。同事问我一些问题,并谈论了他的假期。我回头看屏幕:一个新答案。塔达,再次击败XD
凯文·克鲁伊森

@KevinCruijssen:很典型。我也发生过很多次;)
艾米娜(Emigna)

2

干净,73字节

不使用正则表达式。

import StdEnv,Data.List
$s=or[isPrefixOf s(cycle t)\\t<-tl(tails s)|t>[]]

在线尝试!

定义$ :: [Char] -> Bool
检查给定的字符串是否是从头开始提取的任何子字符串的重复的前缀。


2

C ++(gcc),36个字节

#define f(x)(x+x).find(x,1)<x.size()

在线尝试!

xnor解决方案的另一个端口。使用宏将参数扩展到表达式中。假定参数为类型std::string


1

QlikView变量,27字节

应该将其定义为变量,然后允许您传递参数,例如 $1作为输入值。

它返回0-1(等于QlikView的TRUE()函数)。

=substringcount($1&$1,$1)>2





1

T-SQL,47个字节

使用@Xnor的 方法

DECLARE @ varchar(max)='ababab'

PRINT sign(charindex(@,left(@+@,len(@)*2-1),2))

保留旧的答案,因为它包含一些不错的高尔夫(67字节):

DECLARE @y varchar(max)='abababa'

,@ INT=0WHILE
replace(@y,left(@y,@),'')>''SET
@+=1PRINT @/len(@y)^1

说明:该脚本反复尝试用输入“ @y”的前一个“ @”字符将输入“ @y”替换为空,同时增加“ @”。

如果不使用任何内容替换“ ababab”中的“ ab”,则您有一个空字符串

最终结果将为空。如果在循环变量等于varchar的长度时发生这种情况,则条件为false / 0,因为'@'= len(@y)(没有重复的varchar)。

iif(@=len(@y),0,1)

可以打高尔夫球

@/len(@y)^1

因为'@y'的长度不能为0,并且'@'永远不会超过@y的长度。

在线尝试

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.