53
5
Goal
This is a simple challenge. Your goal is to unscramble a string by swapping each letter with the next letter of the same case, while leaving non-letter characters unchanged.
Step by step explanation
The first character is a
E
. We look for the next letter in upper case: it's aC
. We swap these characters, which leads toCdoE!
.We advance to the next character: this is a
d
. We look for the next letter in lower case: it's ao
. We swap these characters, which leads toCodE!
.We advance to the next character: this is the
d
that we've just moved here. We ignore it, because it has already been processed.We advance to the next character: this is the
E
that was moved here at step #1. We ignore it, because it has already been processed.We advance to the next character: this is a
!
. We ignore it, because it's not a letter.
Rules
You can assume that the input string is made exclusively of printable ASCII characters, in the range 32 - 126.
You may write either a full program or a function, which either prints or returns the result.
If the input string contains an odd number of letters, the last remaining letter can't be swapped with another one and should remain in place, no matter its case. The same logic applies if the string contains an even number of letters, but an odd number of uppercase letters and an odd number of lowercase letters.
This is code-golf, so the shortest answer in bytes wins. Standard loopholes are forbidden.
Test cases
Input : lLEhW OroLd!
Output: hELlO WorLd!
Input : rpGOZmaimgn uplRzse naC DEoO LdGf
Output: prOGRamming puzZles anD COdE GoLf
Input : eIt uqHKC RBWOO xNf ujPMO SzRE HTL EOvd yAg
Output: tHe quICK BROWN fOx juMPS OvER THE LAzy dOg
Input : NraWgCi: Nsas-eNEiTIsev rNsiTG!!
Output: WarNiNg: Case-sENsITive sTriNG!!
Not-so-random test cases:
Input : (^_^)
Output: (^_^)
Input : AWCTY HUOS RETP
Output: WATCH YOUR STEP
Input : hwn oeesd acsp nawyya
Output: who needs caps anyway
Input : SpMycaeIesKyBorekn
Output: MySpaceKeyIsBroken
Input : D's mroyr, Ivam. I'e faardi I act'n od htta.
Output: I'm sorry, Dave. I'm afraid I can't do that.
I assume a similar comment holds if the input contains an even number of letters, but an odd number of uppercase letters and an odd number of lowercase letters. – Greg Martin – 2017-02-04T20:14:00.097
14This is a really clever challenge ... I also like the fact that test cases can be made by typing in a lowercase string, randomly changing some of the letters to uppercase, and then running the exact same program that solves the problem! – Greg Martin – 2017-02-04T20:15:15.187
1@GregMartin I found out that the problem is its own inverse because when trying a test case I accidentally typed in the output instead of the input :-) – Luis Mendo – 2017-02-04T20:17:59.070
I think you should include test cases with more than one non-letter ASCII character ... I think some implementations could accidentally switch them with each other, when that's not supposed to happen. – Greg Martin – 2017-02-04T20:20:59.847
@GregMartin Post edited according to your comments. Thanks! – Arnauld – 2017-02-04T20:31:28.017
3The tests cases should probably include a string without uppercase letters and a string without any letters at all. – Dennis – 2017-02-05T02:51:07.917
Note to self: Read more carefully... I wrote a behemoth that replaced the first x-case letter with the last, not the next. – steenbergh – 2017-02-05T09:17:32.920