57
\$\begingroup\$

Unless you have a userscript that modifies the site's design (or even if so), you should have noticed that we have our site design!

(It's November now)

So, to celebrate, let's make a program that retroactively applies this design (oversimplified, of course)!

So, the most important changes are:

  • our new name is now Code Golf and Coding Challenges
  • our site is no longer the default blue color and is instead a nice dark green

So, given a string, change:

  • PPCG to CGCC
  • Programming Puzzles {non-whitespace} Code Golf to Code Golf {same-thing} Coding Challenges (for example, Programming Puzzles + Code Golf, and Code Golf, and & Code Golf would all be changed to Code Golf + Coding Challenges, and Coding Challenges, and & Coding Challenges.
  • #abc to #acb (swap blue to green and vice versa - just ignore the fact that green shouldn't logically become blue but I don't want to complicate the color shifting)
  • #abcdef to #abefcd (same as above)

Note that for the color swaps, you should accept any hexadecimal digit from 0-9 to a-f. You can choose what case of hex digit to require, but it must be consistent and the same from input to output.

Your substitutions can be case-sensitive, and if not, please specify how the output works.

The substitutions should only happen when the string is surrounded by word boundaries (including the start of the #). In other words, each of the specified substitutions should only occur if the match is at the edge of the string or is bordered by non-alphanumeric characters (on both sides).

Standard loopholes apply. This is a code-golf challenge, so the shortest code wins!

Examples

PPCG -> CGCC
Programming Puzzles or Code Golf -> Code Golf or Coding Challenges
PPCG stands for Programming Puzzles and Code Golf and its site color is #abf -> CGCC stands for Code Golf and Coding Challenges and its site color is #afb
The color #00f is much more intense than #5568ed -> The color #0f0 is much more intense than #55ed68
Programming Puzzles and No Substitution -> Programming Puzzles and No Substitution
No Substitution and Code Golf -> No Substitution and Code Golf
Programming Puzzles and no substitution Code Golf -> Programming Puzzles and no substitution Code Golf
Code Golf and Programming Puzzles -> Code Golf and Programming Puzzles
Programming Puzzles and Programming Puzzles and Code Golf -> Programming Puzzles and Code Golf and Coding Challenges

(for the last test case, it is important to note that the translated string could be translated again but the transformation must be applied exactly once)

Important Update

(Thanks @tsh)

The Programming Puzzles ... Code Golf substitution rule can include the other rules inside of it (Programming Puzzles PPCG Code Golf is valid). In this case, you may choose whether or not the rules are applied, but it must be deterministic. I'm not requiring that you be consistent between PPCG and #... because answers seem to implement the rules in my list ordering which results in inconsistencies. This is just a clarification; I believe all current answers remain valid.

\$\endgroup\$
  • 3
    \$\begingroup\$ Should be apply the substitutions only if there are word boundaries around the substrings or everywhere? \$\endgroup\$ – Erik the Outgolfer Jun 11 at 20:33
  • 1
    \$\begingroup\$ @EriktheOutgolfer Good catch; should have word boundaries. I will specify that; thanks. \$\endgroup\$ – HyperNeutrino Jun 11 at 20:44
  • \$\begingroup\$ Define "word boundary" for a #; regex implementations generally don't consider a # to start a word. \$\endgroup\$ – tomsmeding Jun 11 at 20:59
  • 1
    \$\begingroup\$ Oh, I guess Programming Puzzles and no substitution Code Golf might also catch someone (even though everyone's using the same valid regex) \$\endgroup\$ – Veskah Jun 12 at 12:27
  • 1
    \$\begingroup\$ Suggested test cases Code Golf and Programming Puzzles and Programming Puzzles and Programming Puzzles and Code Golf. @Veskah Hmm, and I think that last suggested test case fails in my 05AB1E answer, since I don't have regex.. >.< Back to the drawing board.. \$\endgroup\$ – Kevin Cruijssen Jun 12 at 12:40

11 Answers 11

12
\$\begingroup\$

Ruby -p, 165 164 159 bytes

It ended up being very similar to the sed answer, but it abuses Ruby's string interpolation to duplicate the hex group matching ([\da-f]{1,2}) within the third regex three times instead of needing to repeat the whole thing again.

  • -1 byte from @randomdude999.
  • -5 bytes from leveraging @Xcali's Perl solution
gsub /\bPPCG\b/,"CGCC"
gsub /\bProgramming Puzzles( \S+ )(Code Golf)\b/,'\2\1Coding Challenges'
[1,2].map{|i|gsub /(^|\s)#\K#{'([\da-f]{%d})'%i*3}\b/,'\2\4\3'}

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Doesn't using {1,2} break with hex inputs of length 4 or 5, e.g. #aabbc? Edit: it does (this example should not be replaced because it's not a valid hex color). \$\endgroup\$ – randomdude999 Jun 11 at 21:33
  • \$\begingroup\$ Fails for this case (- is a non-alphanumeric character). \$\endgroup\$ – Erik the Outgolfer Jun 11 at 21:33
  • \$\begingroup\$ @randomdude999 yeah, good catch. Added a check for that. \$\endgroup\$ – Value Ink Jun 11 at 21:52
  • \$\begingroup\$ @EriktheOutgolfer yeah, I guess. "Word boundaries" with the # is a bit ambiguous since /\b/ doesn't register with it next to another non-alphanumeric, but I did the change anyways for no byte change (replacing \S with \w) \$\endgroup\$ – Value Ink Jun 11 at 21:54
  • \$\begingroup\$ Can't you replace your (?<!\w) with my (^|\W) for 1 char? \$\endgroup\$ – tomsmeding Jun 11 at 21:57
9
\$\begingroup\$

C++ (gcc), 270 285 283 bytes

Thanks to Neil for pointing out a bug.

-2 bytes thanks to ceilingcat.

#import<regex>
#import<string>
auto f=[](auto s){typeof(s)R[][2]{"bPPCG","CGCC","bProgramming Puzzles( \\S+ )(Code Golf)","$2$1Coding Challenges","B#(?=([\\da-f]{3}){1,2}\\b)(.+?)(..??)(..??)","#$2$4$3"};for(auto r:R)s=std::regex_replace(s,std::regex('\\'+*r+"\\b"),r[1]);return s;};

Try it online!

\$\endgroup\$
  • 3
    \$\begingroup\$ Seems to mangle #fade and #faced which it should not. \$\endgroup\$ – Neil Jun 12 at 9:02
6
\$\begingroup\$

Retina 0.8.2, 153 130 bytes

\bPPCG\b
CGCC
\bProgramming Puzzles( \S+ )(Code Golf)\b
$2$1Coding Challenges
\B(#(?=([\da-f]{3}){1,2}\b).+?)(..??)(..??)\b
$1$4$3

Try it online! Link includes test cases. All substitutions are case sensitive. Assumes normal regex word characters are acceptable so that \B# matches only #s that don't follow a word character. Edit: Saved 22 bytes thanks to @tsh.

\$\endgroup\$
  • \$\begingroup\$ Try \B#(?=([\da-f]{3}){1,2}\b)(.+?)(..??)(..??)\b? \$\endgroup\$ – tsh Jun 12 at 6:33
5
\$\begingroup\$

GNU sed -E, 198 chars

s/\bPPCG\b/CGCC/g
s/\bProgramming Puzzles( \S* Cod)e Golf\b/Code Golf\1ing Challenges/g
s/((^|\W)#[0-9a-f])([0-9a-f])([0-9a-f])\b/\1\4\3/g
s/((^|\W)#[0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})\b/\1\4\3/g

Runnable using e.g. sed -E 'the above'; newlines can either be included literally, or replaced with ; if you so wish. Both work.

@HyperNeutrino come on that word boundary rule is stupid. Look what I had to do in the # case.

Yes, I didn't even try. :P

+9 by @Value Ink

\$\endgroup\$
  • 3
    \$\begingroup\$ Flags are no longer included in byte counts so you can take out the extra byte and call it "GNU sed -E" instead. \$\endgroup\$ – Value Ink Jun 11 at 21:10
  • \$\begingroup\$ @ValueInk Whaaaaat? I have apparently been severely out of touch with this community for too long to not notice that. I think it's a good rule though. Also, thanks for mentioning. \$\endgroup\$ – tomsmeding Jun 11 at 21:14
  • \$\begingroup\$ doesn't sed's regex matching allow using \d as a shortcut for 0-9? could save you a whole 6 bytes \$\endgroup\$ – randomdude999 Jun 11 at 21:22
  • \$\begingroup\$ Also I just noticed, you return "Programming Puzzles or Coding Challenges" for the second test case instead of the expected "Code Golf or Coding Challenges". \$\endgroup\$ – Value Ink Jun 11 at 21:24
  • \$\begingroup\$ @randomdude999 The re_format(7) man page on my Mac seems to suggest that sed should support \d, but apparently it doesn't. ¯\_(ツ)_/¯ \$\endgroup\$ – tomsmeding Jun 11 at 21:45
4
\$\begingroup\$

Stax, 85 bytes

ì▀¼FΣ¼≤C╛╓ÄydîNû►┘Δ▲Bd♫|α╒oñFτ▒t!↑▌╩┘♦pMc6Hèé▄·│╝∙↔¥^4b5╠·9█&╨^╨♂═î£ε■屫\┴J₧å♠Å≡z╜û♀

Run and debug it

\$\endgroup\$
4
\$\begingroup\$

05AB1E, 123 109 105 110 114 bytes

žKISå_Å¡JεÐć'#QsžhA6£«sSåP*i3äćsRJ«ë"PPCG"Qi"CGCC"]J”–±ÇÀ”DU¡ćsε”ƒËŠˆ”©¡DVćDÁ2ôεðå}ćs_P*YyÊP*i”Âïªï”«s®ý«®ìëyXì]J«

+5 bytes fixing test cases like Programming Puzzles and no substitution Code Golf and Programming Puzzles and Programming Puzzles and Code Golf.
+4 bytes fixing test cases like color-#00f (colors with something besides spaces/newlines surrounding it). Thanks to @Grimy for bringing this to my attention.

Case-sensitive. Hexadecimal values are with lowercase abcdef; Programming Puzzles ... Code Golf is in titlecase; PPCG is in full uppercase.

Try it online.

Definitely not the right language for the job.. Mimicking word-boundaries and replacing Programming Puzzles \S+ Code Golf, but not Code Golf \S+ Programming Puzzles or Programming Puzzles \S+ \S+ Code Golf without any regexes is pretty hard (to do short).. >.>

Explanation:

žK                # Push "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
                  # (NOTE: if '_' also count as word boundary, use `žj` instead)
  IS              # Push the input as a list of characters
    å_            # Check for each character if they are NOT in the string
      Å¡          # Split the (implicit) input on truthy values
        J         # Join each inner character list to a string again
ε                 # Map each word to:
 Ð                #    Triplicate the word
  ć               #    Extract head; push remainder and head separately to the stack
   '#Q           '#    Check if the head equals "#"
    žh            #    Push string "0123456789"
      A6£«        #    Append the first 6 letters of the alphabet: "0123456789abcdef"
   s      sSåP    #    Check if the characters of the remainder are all in this string
   *i             #    If both are truthy:
     3ä           #     Split the 'word' into three parts
                  #      i.e. "#ab12cd" → ["#ab","12","cd"]
       ćs         #     Extract head, and swap
         R        #     Reverse the remainder list
          J«      #     Join them together, and merge them to the head again
    ë"PPCG"Qi     #    Else-if the word is "PPCG":
     "CGCC"       #     Push "CGCC"
                  #    (Implicit else:
                  #      Use the word that's still there from the initial triplicate)
]                 # Close all if statements and the nested map
 J                # Join the mapped words together again
”–±ÇÀ”            # Push dictionary string "Programming Puzzles"
      DU          # Save a copy in variable `X`
        ¡         # Split the string by this
         ćs       # Extract head & swap; pushing head and remainder to the stack
ε                 # Map each substring `y` in the remainder to:
 ”ƒËŠˆ”           #  Push dictionary string "Code Golf"
       ©          #  Save it in variable `®` (without popping)
        ¡         #  Split the current substring we're mapping by it
         DV       #  Save a copy of this list in variable `Y`
           ćD     #  Extract the head and duplicate
                  #  (so the stack is: remainder, head, head)
 Á                #  Rotate the characters in the head-string once towards the right
  2ô              #  Split it into parts of size 2
    εðå}          #  Check in each part if it contains a space
        ćs        #  Extract head and swap again
          _       #  Check if all values are 0
           P      #  And check if this is truthy for all
          *       #  And check if this is truthy, as well as the head
                  #  (this means the current string has a leading and trailing space,
                  #   and no other spaces)
 YyÊP             #   Check that none of the susbtrings in variable `Y`
                  #   are equal to the current substring `y`
 *i               #   If both checks above are truthy:
   ”Âïªï”«        #    Prepend "Coding Challenges" to the duplicated head
          s®ý     #    Join the remainder by variable `®` ("Code Golf")
             «    #    Append it
              ®ì  #    And prepend an additional variable `®` ("Code Golf")
  ë               #   Else:
   y              #    Simply keep the substring `y` as is
    Xì            #    And prepend variable `X` ("Programming Puzzles") 
                  #    since we've split by it
]                 # Close all if-else statements and the map
 J                # Join the mapped substrings together to a single string
  «               # And append it to the initially extracted head
                  # (then output the resulting string implicitly as result)

See this 05AB1E tip of mine (section How to use the dictionary?) to understand why ”–±ÇÀ” is "Programming Puzzles"; ”ƒËŠˆ” is "Code Golf"; and ”Âïªï” is "Coding Challenges".

\$\endgroup\$
3
\$\begingroup\$

Python 2, 240 bytes

import re
lambda x,s=re.sub,b='(?<!\w)',e='(?!\w)',h='([\da-f]',t=r'#\1\3\2':s(b+'#%s{2})'%h+h+'{2})%s{2})'%h+e,t,s(b+'#%s)'%h+h+')%s)'%h+e,t,s(b+'Programming Puzzles( \S+ Cod)e Golf'+e,r'Code Golf\1ing Challenges',s(b+'PPCG'+e,'CGCC',x))))

Try it online!

\$\endgroup\$
3
\$\begingroup\$

JavaScript (Node.js), 174 bytes

s=>s[R='replace'](/\bPPCG\b/g,'CGCC')[R](/\bProgramming Puzzles( \S+ )(Code Golf)\b/g,'$2$1Coding Challenges')[R](/\B#(?=([\da-f]{3}){1,2}\b)(.+?)(..??)(..??)\b/ig,'#$2$4$3')

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Fails on test case #abcde because the regex qualifier {3,6} matches between 3 and 6 characters, instead of either 3 or 6 which I assume you were going for. \$\endgroup\$ – Value Ink Jun 12 at 3:12
  • \$\begingroup\$ @ValueInk nice catch. fixed with +5 bytes. \$\endgroup\$ – tsh Jun 12 at 3:30
  • \$\begingroup\$ Might be shorter to use a replace function over the long regex \$\endgroup\$ – Downgoat Jun 12 at 6:21
2
\$\begingroup\$

Pyth, 177 173 162 142 bytes

J::jb.z"\\bPPCG\\b""CGCC"." z¶NZI°Pÿúd(MÜ_BöIkxnqä'u)"." s6#~ÍN³=<nñu/GÎg"VS2~:J%"(^|\W)#%s\\b"*3%"([\da-f]{%d})"N$r"\1#\2\4\3"$)J

Here's a version without Pyth's string compression mechanisms (aka it's safe to copy-paste):

J::jb.z"\\bPPCG\\b""CGCC""\\bProgramming Puzzles( \S+ )(Code Golf)\\b""\\2\\1Coding Challenges"VS2~:J%"(^|\W)#%s\\b"*3%"([\da-f]{%d})"N$r"\1#\2\4\3"$)J

Try it online!

This ended up being really long because I tried to be as pedantic as possible with the regexes. I tried to compress every string possible, but most of them either didn't get smaller or couldn't be pasted into TIO properly.

Explanation:

J::                      # definition of J to the following 2 regex replacements
   jb.z                  # input to first regex replacement: all input lines joined together
   "\\bPPCG\\b"          # first regex
   "CGCC"                # first replacement
   ."<compressed>"       # second regex: "\\bProgramming Puzzles( \S+ )(Code Golf)\\b"
   ."<compressed>"       # second replacement: "\\2\\1Coding Challenges"
VS2                      # loop twice, N = 1 or 2
  ~:J                    # some weird assignment: J = regex replace in J (would be J := (regex, replacement) if : was python's regex replace operator)
    %                    # third regex: string format
     "(^|\W)#%s\\b"      # format string
     *3                  # repeat 3 times:
       %"([\da-f]{%d})"N # string format, replace %d with N (the loop counter)
    $r"\1#\2\4\3"$       # third replacement: uses python raw literals because it's shorter than escaping the backslashes
    )                    # end for loop
J                        # print J
  • -11 thanks to a better regex from Value Ink's Ruby answer
  • -20 thanks to using a loop for both of the hex replacements, inspired by the Ruby and Perl answers
\$\endgroup\$
1
\$\begingroup\$

Perl 5 -p, 152 145 bytes

@ValueInk saves 7 bytes

s/\bPPCG\b/CGCC/g;s/\bProgramming Puzzles( \S+ )(Code Golf)\b/$2$1Coding Challenges/g;for$a(1,2){$p="([a-f0-9]{$a})"x3;s/(^|\s)#\K$p\b/$2$4$3/gi}

Try it online!

\$\endgroup\$
  • \$\begingroup\$ ( \S+ )(Code Golf)\b/$2$1Coding saves 2 bytes. Also the last regex can end with just a \b instead of (?=\s|$) \$\endgroup\$ – Value Ink Jun 12 at 1:49
  • \$\begingroup\$ I was working on that first one while you were typing that comment. I've made the other change to save some bytes. Thanks! \$\endgroup\$ – Xcali Jun 12 at 1:52
  • \$\begingroup\$ That \s should be \W instead, otherwise it fails this case (- is a non-alphanumeric character, so the substitution should be applied). \$\endgroup\$ – Grimy Jun 12 at 20:01
  • \$\begingroup\$ 137 \$\endgroup\$ – Grimy Jun 12 at 20:23
0
\$\begingroup\$

Java 8, 192 bytes

s->s.replaceAll("\\bPPCG\\b","CGCC").replaceAll("\\bProgramming Puzzles( \\S+ )(Code Golf)\\b","$2$1Coding Challenges").replaceAll("\\B(#(?=([0-9a-f]{3}){1,2}\\b).+?)(..??)(..??)\\b","$1$4$3")

Port of @Neil's Retina answer, so make sure to upvote him!

Try it online.

\$\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.