子串链化


27

介绍

在此示例中,让我们使用字符串Hello, World!和数组[3, 2, 3]。为了找到子字符串链,我们经历以下过程:

数组的第一个数字是3,所以我们得到的字符串[0 - 3],这是Hel。之后,我们3从初始字符串中删除了前几个字符,从而使我们有了lo, World!

数组的第二个数字是2,因此我们[0 - 2]从新字符串中获得子字符串,从而得到lo。剩余的字符串变为, World!

最后一个数字是a 3,它给我们, W。该子串链是所有子组合,这给我们的:

['Hel', 'lo', ', W']

对于更直观的示例:

[3, 2, 3], 'Hello, World!'
3 -> Hel
2 ->    lo
3 ->      , W

任务

给定一个非空字符串一个仅由正整数> 0)组成的非空数组,输出子字符串chain。您可以假定数组中所有整数的总和不超过字符串的长度。

您还可以假定字符串永远不会包含任何换行符。

测试用例

Input: abcdefghijk, [2, 1, 3]
Output: ['ab', 'c', 'def']

Input: Code Golf, [4, 1]
Output: ['Code', ' ']

Input: Ayyy, [3]
Output: ['Ayy']

Input: lexicographically, [2, 2, 2, 7, 4]
Output: ['le', 'xi', 'co', 'graphic', 'ally']

这是,因此字节数最少的提交将获胜!

Answers:



12

Python 2,42字节

s,a=input()
for n in a:print s[:n];s=s[n:]

有时您只是无聊地做。


到目前为止,最短的python答案中最短的答案
Cyoce

好吧,显然我想得太多了,哈哈...
DJMcMayhem

8

Brachylog20 13字节

h@[~c.:la~t?,

在线尝试!

这是非常低效的,并且在最后一个测试用例上在TIO上超时。

说明

Input = [String, List of integers]

h@[            Take a prefix of the string
   ~c.         Take a possible list of strings which when concatenated results in that prefix
      :la      Take the lengths of each element of that list
         ~t?,  This list of lengths is equal to the list of integers of the Input

效率更高的版本,15字节

t:{〜l} a。,?h @ [〜c


8

Python 3,45个字节

f=lambda s,a:f(s[a[0]:print(s[:a.pop(0)])],a)

这将在每行打印一个子字符串,并在a耗尽时错误终止。

repl.it对其进行测试。


2
偷偷摸摸打印的好方法!
xnor

7

Python,第52,46个字节

f=lambda a,s:a and[s[:a[0]]]+f(a[1:],s[a[0]:])

递归lambda函数。

感谢Dennis削减了6个字节!


7

果冻,6个字节

Jx$ĠịY

在线尝试!

        The implicit working value is the first argument.
Jx$     Given a list L, repeat (x) an element of [1..len(n)] (J)
        as many times as the corresponding value in L.
   Ġ    Group indices by values. This turns [1, 1, 1, 2, 2, 3, 3]
        into [[1, 2, 3], [4, 5], [6, 7]].
    ị   Index into the second argument.
     Y  Join by newlines.

5

Haskell,34个字节

s#(a:b)=take a s:drop a s#b
_#_=[]

用法示例:"lexicographically" # [2,2,2,7,4]->["le","xi","co","graphic","ally"]

简单递归。

或通过内置的无聊的29字节解决方案:

import Data.Lists
splitPlaces

5

Ruby,26个字节

->w,a{a.map{|n|w.shift n}}

字符串表示为字符数组。


4

PowerShell v2 +,46个字节

param($a,$b)$b|%{-join$a[$i..($i+=$_-1)];$i++}

接受输入字符串$a和数组$b,循环遍历$b。每次迭代都会$a根据$i(默认为$null0)和当前数字进行数组切片。需要执行-1和,$i++因为PowerShell中的字符串是零索引的。

例子

(此处的输出以空格分隔,因为这是数组的默认字符串化方法)

PS C:\Tools\Scripts\golfing> @('abcdefghijk',@(2,1,3)),@('Code Golf',@(4,1)),@('Ayyy',@(3)),@('lexicographically',@(2,2,2,7,4))|%{""+$_[0]+" -> "+(.\substring-chainification.ps1 $_[0] $_[1])}
abcdefghijk -> ab c def
Code Golf -> Code  
Ayyy -> Ayy
lexicographically -> le xi co graphic ally

4

Perl,28个字节

包括+1的 -n

使用STDIN上的输入字符串,然后在单独的行上输入每个数字:

(echo "Hello, World!"; echo 3; echo 2; echo 3) | perl -nE 'say for/(??{"."x<>||"^"})/g'

只是代码:

say for/(??{"."x<>||"^"})/g

23字节的版本||"^"也没有进行任何工作,但是会打印出虚假的尾随换行符

"^"$_如果字符串不包含正则表达式元字符,则可以替换为


3

MATL,8字节

ys:)1bY{

在线尝试!

说明

y    % Implicitly take the two inputs: numerical array, string. Duplicate the array
s    % Sum of the array, say n
:    % Range from 1 to n
)    % Take first n characters of the string
1    % Push 1
b    % Bubble up the original copy of the string to the top
Y{   % Split into pieces of lengths given by the numerical array. The pieces are 
     % stored in a cell array, which is implicitly displayed, one cell per line

3

JavaScript(ES6),39 38 35字节

由于ETHproductions节省了3个字节:

s=>a=>a.map(v=>s.slice(t,t+=v),t=0)

例:

//Definition
f=
s=>a=>a.map(v=>s.slice(t,t+=v),t=0)

//Call
f('lexicographically')([2, 2, 2, 7, 4]);

//Output
Array [ "le", "xi", "co", "graphic", "ally" ]


先前的解决方案:
借助Huntro,获得了38个字节:

s=>a=>a.map(v=>s.substr(t,v,t+=v),t=0)

39个字节:

(s,a)=>a.map(v=>s.substr(t,v,t+=v),t=0)

1
您可以通过
巡回

2
.slice保存一些字节:s=>a=>a.map(v=>s.slice(t,t+=v),t=0)
ETHproductions 2016年

3

批处理,74字节

@set/ps=
@for %%i in (%*)do @call echo %%s:~0,%%i%%&call set s=%%s:~%%i%%

我在打C吗?这是不对的!将STDIN上的字符串和数组作为命令行参数。


3

Java,119字节

String[] substringChainification(String s, int[] i) {
    String[] r = new String[i.length];
    int j = 0, f = 0;
    for (int t : i)
        r[j++] = s.substring(f, f += t);
    return r;
}

打高尔夫球:

String[]s(String s,int[]i){String[]r=new String[i.length];int j=0,f=0;for(int t:i)r[j++]=s.substring(f,f+=t);return r;}

我修改了RomanGräf的答案(/codegolf//a/93992/59935),但是我没有足够的代表发表评论。

我更改了循环实现,而不是在每次迭代中都将源字符串设置为另一个子字符串,而只是更改获取子字符串的索引。


2
欢迎来到PPCG!很棒的第一篇文章!这正是您应该对高尔夫提出的建议,但代表不足。
Rɪᴋᴇʀ

1
欢迎来到PPCG!我同意_EasterlyIrk_的第一好文章。我试图找到更多可以打高尔夫球的东西,但是没有。也许您已经看过它,但是您可能会发现有趣的Java高尔夫技巧。再次欢迎您,并祝您逗留愉快。
凯文·克鲁伊森


2

sed(82 + 2--rn)84

s,^,\n,;:l;N;s,\n\n,\n,;:
s,^([^\n]*)\n(.)([^\n]*\n)1,\1\2\n\3,
t;P;s,^[^\n]*,,;tl

输入的第一行是字符串。然后,此后的每一行都是一元字符串的大小(一元)

例:

$ cat test.txt:
lexicographically
11
11
11
1111111
1111

$ cat hold | sed -rnf sed.txt
le
xi
co
graphic
ally

2

CJam,11个字节

lq~{/(ns}/;

在线尝试!

说明

l    e# Read input string.
q~   e# Read array of lengths and eval.
{    e# For each length...
  /  e#   Split the string into chunks of the given size.
  (  e#   Pull off the first chunk.
  n  e#   Print with linefeed.
  s  e#   Flatten the remaining chunks into a single string again.
}/
;    e# Discard any remainder of the input string.

2

C,81个字节

i,j;f(s,l,k)char*s;int*l;{for(i=j=0;i<k;){write(1,s+j,l[i]);puts("");j+=l[i++];}}

因为write()没有缓冲输出,所以任何在线编译器都很难输出它。

test.c

i,j;f(s,l,k)char*s;int*l;{for(i=j=0;i<k;){write(1,s+j,l[i]);puts("");j+=l[i++];}}
main(){
    int l[]={3,2,3};
    f("Hello, World!",l,3);
    int ll[]={2,1,3};
    f("abcdefghijk",ll,3);
    int lll[]={4,1};
    f("Code Golf",lll,2);
    int llll[]={3};
    f("Ayyy",llll,1);
    int lllll[]={2,2,2,7,4};
    f("lexicographically",lllll,5);
}

输出不带管道:

Hel
lo
, W
ab
c
def
Code

Ayy
le
xi
co
graphic
ally

在ideone编译器中,上述c程序的输出[将第一个功能显示在屏幕上更高的位置上]是“ Hello,WabcdefCode Ayylexicographically”而没有“ \ n” ...
RosLuP

2

PHP,98字节

<?php
$b=$argv[1];foreach(explode(',',$argv[2])as$a){echo(substr($b,0,$a).' ');$b=substr($b,$a);}

用法:

php chainification.php lexicographically 2,2,2,7,4


输出:

le xi co graphic ally


PHP可能有更好的解决方案。


2

PHP,82字节

<?php for($s=$argv[++$i],$j=-1;$n=$argv[++$i];){for(;$n--;)echo$s[++$j];echo"
";}

将输入作为字符串,然后是数字列表,输出用换行分隔。例如

php chainify.php lexicographically 2 2 2 7 4

如果您是能够与-r一起使用$ argv的人之一,则可以保存用于开始标记的6个字节。


我对的使用感到困惑$argv[++$i]。为什么不$argv[1]$argv[2]
MonkeyZeus

另外,在sandbox.onlinephpfunctions.com使用PHP 7.0.2,我达到了3秒的时间限制
MonkeyZeus

这不是$argv[2]因为我们需要遍历提供的参数,这是$argv[++$i]第一次避免使用a ,$i=1并因此节省了2个字节。
user59178

2

PHP,63字节

<?foreach($_GET[a]as$p){echo" ".substr($_GET[s],$s,$p);$s+=$p;}

输出为数组85字节

<?foreach($_GET["a"]as$p){$o[]=substr($_GET["s"],$s,$p);$s+=$p;}echo json_encode($o);

1

Pyth,7个字节

PcwsM._

接受由换行符分隔的输入,字符串不转义并且在数组之后。 在线尝试!

说明:

     ._  Get all prefixes of Q
   sM    Map sum across each of these prefixes (to get the total indices)
 cw      Split the string at these locations
P        Remove the last "remainder" of the string

1

八度/ MATLAB,31字节

@(s,a)mat2cell(s(1:sum(a)),1,a)

这是一个带有输入的匿名函数s:string; a:数值数组。

在Ideone尝试一下

说明

这是我的MATL答案的端口。

s(1:sum(a))        % Take first n characters of string s, where n is the sum of array a
mat2cell(...,1,a)  % Split into pieces of lengths given by a and store in a cell array

1

Java 142字节

public static String[]substringChain(String s,int[]i){
  String[]r=new String[i.length];
  for(int j=-1;++j<i.length;){
    r[j]=s.substring(0,i[j]);
    s=s.substring(i[j]);
  }
  return b;
}

打高尔夫球:

String[]s(String s,int[]i){String[]r=new String[i.length];for(int j=-1;++j<i.length;){r[j]=s.substring(0,i[j]);s=s.substring(i[j]);}return b;}

1

Awk,36个字符

{FIELDWIDTHS=$0;OFS=RS;getline}$1=$1

样品运行:

bash-4.3$ awk '{FIELDWIDTHS=$0;OFS=RS;getline}$1=$1' <<< $'3 2 3\nHello, World!'
Hel
lo
, W

在现实生活中,我会这样使用它,只是不知道如何计算其分数:

bash-4.3$ awk -vFIELDWIDTHS='3 2 3' -vOFS='\n' '$1=$1' <<< 'Hello, World!'
Hel
lo
, W


1

GNU sed,55 + 2(rn个标志)= 57个字节

1H;1d;G;:;s=.(\n.*)\n(.)=\1\2\n=;t;s=.==;P;s=[^\n]*==;h

在线尝试!(感谢@Dennis添加sed)

说明:输入字符串应在第一行,数字在一进制中,在此之后应在单独的行中。在周期开始时会隐式读取新行,每次都运行脚本。

1H;1d                       # once: append string to hold space and start new cycle
                            #Initially, the hold space contains an useful '\n'.
G                           # append hold space to pattern space. The pattern space
                            #format will be: 'UNARY\n\nSTRING'.
:;s=.(\n.*)\n(.)=\1\2\n=;t  # iteratively remove a char from the string, as many
                            #times as unary chars, and store it on 2nd pattern line
s=.==;P                     # remove '\n', then print the new top line
s=[^\n]*==;h                # delete up to '\n' and update hold space

测试运行:使用带有EOF的此处文档作为结束标记

sed -rnf program.sed << EOF
> abcdefghijk
> 00
> 0
> 000
> EOF

输出:

ab
c
def

1

Vimscript,79 78字节

不是很漂亮,我敢肯定它可以改善...

带一个vim缓冲区,然后调用echom string(A([2,3]))以查看输出

fu A(l)
let r=[]
for i in a:l
exe "norm d".i."l"
let r+=[@"]
endfo
retu r
endf

我实际上想到了欺骗并输出字符串 ["abc", "def"] ...但是我拒绝了:P

说明:删除(放入默认寄存器)每个数组项的字符数量并将其添加到数组中r……确实是一个无聊的答案。


1

Common Lisp,78 76字节

假设允许匿名函数:

(lambda(s l)(loop for x in l as y = x then(+ y x)collect(subseq s(- y x)y)))

用法

(funcall #'(lambda(s l)(loop for x in l as y = x then(+ y x)collect(subseq s(- y x)y)))"AbCdefGhijK"'(3 2 3))

输出量

("AbC" "de" "fGh")

-2个字节,方法是使用as代替and和更改y定义以适合两个变量之间的括号(subseq ...)


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.