11
\$\begingroup\$

Introduction

I'm a real big fan of the SBU (Short But Unique) challenges that crop up on PPCG all of the time. The CUSRS is a system designed to refactor strings, a CUSRS function takes 2 parameters and outputs 1 String.

Challenge

Produce a program, function, lambda or acceptable alternative to do the following:

Given String input and String refactor (as examples), refactor input using refactor as follows:

The refactor String will be in the format of ((\+|\-)\w* *)+ (regex), for example:

+Code -Golf -lf +al

Each section is a refactoring action to perform on input. Each program also has a pointer.

+ Will insert it's suffix (without the plus) at the pointers current location in the String and then reset the pointer to 0.

Each operation should be applied to the input String and the result should be returned.

Example:

input:
Golf +Code //pointer location: 0

output:
CodeGolf //pointer location: 0

- Will increment the pointer through the String until it finds the suffix. The suffix will be removed from the String and the pointer will be left on the left side of the removed text. If no suffix is found the pointer will simply progress to the end of the String and be left there.

input:
Golf -lf //pointer location 0

output:
Go //pointer location 2

Examples

input:
"Simple" "-impl +nip -e +er"

output:
"Sniper"

input:
"Function" "-F +Conj"

output:
"Conjunction"

input:
"Goal" "+Code -al +lf"

output:
"CodeGolf"

input:
"Chocolate" "Chocolate"

output:
"Chocolate" //Nothing happens...

input:
"Hello" "-lo+p        +Please" //Spaces are irrelevant

output:
"PleaseHelp"

input:
"Mississippi" "-s-s-i-ppi+ng" //Operations can be in any order

output:
"Missing"

input:
"abcb" "-c -b +d"

output:
"abd"

input:
"1+1=2" "-1+22-=2+=23"

outut:
"22+1=23"

Example Code

The example is Java, it's not golfed at all.

public static String refactor(String input, String swap) {
    int pointer = 0;
    String[] commands = swap.replace(" ", "").split("(?=[-+])");

    for (String s : commands) {
        if (s.startsWith("+")) {
            input = input.substring(0, pointer) + s.substring(1) + input.substring(pointer, input.length());
            pointer = 0;
        } else {
            if (s.startsWith("-")) {
                String remove = s.substring(1);
                for (int i = pointer; i < input.length(); i++) {
                    if (input.substring(i, i + remove.length() > input.length() ? input.length() : i + remove.length()).equals(remove)) {
                        pointer = i;
                        input = input.substring(0, i) + input.substring(i + remove.length(), input.length());
                        break;
                    }
                }
            }
        }
    }

    return input;
}

Rules

  • Standard Loopholes Apply
  • Shortest code, in bytes, wins
| improve this question | | | | |
\$\endgroup\$
  • 1
    \$\begingroup\$ Related \$\endgroup\$ – Emigna Nov 24 '16 at 16:50
  • \$\begingroup\$ What should be the output for aaa -a? \$\endgroup\$ – ETHproductions Nov 24 '16 at 16:51
  • \$\begingroup\$ |aa with the pipe being the pointer. \$\endgroup\$ – Shaun Wild Nov 24 '16 at 16:51
  • \$\begingroup\$ @Emigna Upon looking at the question in question, I believe the implementation of mine would be much different. \$\endgroup\$ – Shaun Wild Nov 24 '16 at 17:01
  • \$\begingroup\$ What happens with - if the suffix isn't found? \$\endgroup\$ – Zgarb Nov 24 '16 at 17:19
1
\$\begingroup\$

APL, 91 90 bytes

{s l←⍵0⋄s⊣{g←1↓⍵⋄'+'=⊃⍵:+s∘←(l↑s),g,l↓s⋄l∘←¯1+1⍳⍨g⍷s⋄+s∘←(l↑s),s↓⍨l+⍴g}¨{1↓¨⍵⊂⍨⍵=⊃⍵}' ',⍺}

This takes the string as its right argument, and the commands as its left argument, like so:

      '+Code -al +lf' {s l←⍵0⋄s⊣{g←1↓⍵⋄'+'=⊃⍵:+s∘←(l↑s),g,l↓s⋄l∘←¯1+1⍳⍨g⍷s⋄+s∘←(l↑s),s↓⍨l+⍴g}¨{1↓¨⍵⊂⍨⍵=⊃⍵}' ',⍺} 'Goal'
CodeGolf
| improve this answer | | | | |
\$\endgroup\$
1
\$\begingroup\$

GolfScript, 97 Bytes

" "%(:s;0:p;{("-"0=={.s p>\?.-1={;;s,:p;}{:p;,:l;s p<s p l+>+:s;}if}{s p<\+s p>+:s;0:p;}if}/"\n"s

Test: golfscript.tryitonline.net

| improve this answer | | | | |
\$\endgroup\$
  • \$\begingroup\$ Welcome to PPCG! You can use the interpreter on Try it online, which does support input. \$\endgroup\$ – Martin Ender Nov 25 '16 at 10:27
1
\$\begingroup\$

Python 3 (164 194 186 181 168 165 bytes)

p=0
w,*x=input().split()
for i in x:
 if '-'>i:w,p=w[:p]+i[1:]+w[p:],0
 else:
  try:p=w.index(i[1:],p)
  except:p=len(w)
  w=w[:p]+w[p:].replace(i[1:],'',1)
print(w)

Example demonstrating the pointer moving to the end if it doesn't find a substring:

Input: HelloThere -x +Friend
Output: HelloThereFriend

Special thanks to Artyer for saving me 13 bytes.

Another thanks to Artyer for saving me another 3 bytes via the beg parameter of index.

Old answer:

p=0
x=input().split()
w=x[0]
for i in x[1:]:
 if i[0]=='+':
  w=w[:p]+i[1:]+w[p:]
  p=0
 else:
  p=w[p:].index(i[1:])+p
  w=w[:p]+w[p:].replace(i[1:],'',1)
print(w)

Example demonstrating the pointer works (all the examples in the Q work even if you don't factor in the pointer and simply replace on first occurence):

Input: HelloThereCowboy -r -e -y +ySays +Oh
Output: OhHelloTheCowboySays

Edit: Since 2 minutes ago my answer is now invalid according to a comment by the asker.

aaa -b +b would result with aaab because the pointer would go all the way to the end.

Edit2: Fixed.

| improve this answer | | | | |
\$\endgroup\$
  • 1
    \$\begingroup\$ w,*x=input().split(), and if'-'>i: instead of if i[0]=='+':and tab character for 2 indents instead of 2 spaces will save some bytes \$\endgroup\$ – Artyer Nov 24 '16 at 19:07
  • \$\begingroup\$ If I try to mix tabs and spaces I get TabError: inconsistent use of tabs and spaces in indentation. Thanks for the suggestions, I didn't know about those features! I'll begin adding them immediately. \$\endgroup\$ – redstarcoder Nov 24 '16 at 21:03
  • \$\begingroup\$ @redstartcoder I guess the tab trick only works in Python 2. My bad \$\endgroup\$ – Artyer Nov 24 '16 at 22:22
  • \$\begingroup\$ I could absolutely be wrong here, but I think strings have a find method which will return -1 if it can't find the substring. Since -1 points to the back of the string, all you would need to do is take a modulus of p by the length of w which should mean you don't need a try-except. \$\endgroup\$ – Kade Nov 25 '16 at 19:35
  • 1
    \$\begingroup\$ You would do -1%len(str) to get the index at the end of string. str.index and str.find also take a start parameter, so I assume you can replace w[p:].index(i[1:]) with w.index(i[1:],p). Overall, it would be else:p=(w.find(i[1:],p)+p)%len(p);w=w[:p]+w[p:].replace(i[1:],'',1). \$\endgroup\$ – Artyer Nov 26 '16 at 0:33
0
\$\begingroup\$

JavaScript (ES6), 117 bytes

(s,r,t='')=>r.match(/\S\w*/g).map(r=>(q=r.slice(1),r<'-'?(s=t+q+s.t=''):([b,...a]=s.split(q),t+=b,s=a.join(q))))&&t+s

Explanation: Instead of using a cumbersome pointer, I keep the left half of the string in t and the right half in s. Additionally, split and join are a convenient way to perform the removal.

| improve this answer | | | | |
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.