Jump to content
Claris Engage 2025 - March 25-26 Austin Texas ×

This topic is 5249 days old. Please don't post here. Open a new topic instead.

Recommended Posts

Posted

Here's a new puzzler....

Build a Rot13() custom function.

It should take a string and rotate each letter 13 places in the alphabet. Wiki Rot13 for more details. The function should only affect the letters on a string: A-Z and a-z.

If you don't have Advanced, do the above, but for single characters and wrap it in a Looping script.

Bonus points if you can do a string without a recursive custom function or looping. (I couldn't figure out how.)

Bonus points if you build it so any integer can be entered as a parameter in the function, creating a general Caesar cipher.

To keep it interesting, don't refer to any Filemaker resources outside of the FMP help files (ie no searching this site, or Dunning's custom function site, etc).

Tbbq yhpx!

Posted

No recursive or looping.

It does require that the original text not contain any sequence that looks like "_nn_" where nn is a two digit number from 1 to 26. If there is likely to be such an odd string, you can change the intermediate format to something even more obscure.

/* Rot13(text) */

/* */

Substitute(

Substitute(

text;

["a";"_01_"]; ["b";"_02_"]; ["c";"_03_"]; ["d";"_04_"]; ["e";"_05_"];

["f";"_06_"]; ["g";"_07_"]; ["h";"_08_"]; ["i";"_09_"]; ["j";"_10_"];

["k";"_11_"]; ["l";"_12_"]; ["m";"_13_"]; ["n";"_14_"];["o";"_15_"];

["p";"_16_"]; ["q";"_17_"]; ["r";"_18_"]; ["s";"_19_"]; ["t";"_20_"];

["u";"_21_"]; ["v";"_22_"]; ["w";"_23_"]; ["x";"_24_"]; ["y";"_25_"];

["z";"_26_"]);

["_01_";"n"]; ["_02_";"o"]; ["_03_";"p"]; ["_04_";"q"]; ["_05_";"r"];

["_06_";"s"]; ["_07_";"t"]; ["_08_";"u"]; ["_09_";"v"]; ["_10_";"w"];

["_11_";"x"]; ["_12_";"y"]; ["_13_";"z"]; ["_14_";"a"];["_15_";"b"];

["_16_";"c"]; ["_17_";"d"]; ["_18_";"e"]; ["_19_";"f"]; ["_20_";"g"];

["_21_";"h"]; ["_22_";"i"]; ["_23_";"j"]; ["_24_";"k"]; ["_25_";"l"];

["_26_";"m"]

)

Posted

/* CeasarCipher(text; offset) */

/* */

Substitute(

Substitute(

text;

["a";"_" & Mod(1 + offset;26) & "_"]; ["b";"_" & Mod(2 + offset;26) & "_"]; ["c";"_" & Mod(3 + offset;26) & "_"];

["d";"_" & Mod(4 + offset;26) & "_"]; ["e";"_" & Mod(5 + offset;26) & "_"]; ["f";"_" & Mod(6 + offset;26) & "_"];

["g";"_" & Mod(7 + offset;26) & "_"]; ["h";"_" & Mod(8 + offset;26) & "_"]; ["i";"_" & Mod(9 + offset;26) & "_"];

["j";"_" & Mod(10 + offset;26) & "_"]; ["k";"_" & Mod(11 + offset;26) & "_"]; ["l";"_" & Mod(12 + offset;26) & "_"];

["m";"_" & Mod(13 + offset;26) & "_"]; ["n";"_" & Mod(14 + offset;26) & "_"];["o";"_" & Mod(15 + offset;26) & "_"];

["p";"_" & Mod(16 + offset;26) & "_"]; ["q";"_" & Mod(17 + offset;26) & "_"]; ["r";"_" & Mod(18 + offset;26) & "_"];

["s";"_" & Mod(19 + offset;26) & "_"]; ["t";"_" & Mod(20 + offset;26) & "_"]; ["u";"_" & Mod(21 + offset;26) & "_"];

["v";"_" & Mod(22 + offset;26) & "_"]; ["w";"_" & Mod(23 + offset;26) & "_"]; ["x";"_" & Mod(24 + offset;26) & "_"];

["y";"_" & Mod(25 + offset;26) & "_"]; ["z";"_" & Mod(26 + offset;26) & "_"]);

["_1_";"a"]; ["_2_";"b"]; ["_3_";"c"]; ["_4_";"d"]; ["_5_";"e"];

["_6_";"f"]; ["_7_";"g"]; ["_8_";"h"]; ["_9_";"i"]; ["_10_";"j"];

["_11_";"k"]; ["_12_";"l"]; ["_13_";"m"]; ["_14_";"n"];["_15_";"o"];

["_16_";"p"]; ["_17_";"q"]; ["_18_";"r"]; ["_19_";"s"]; ["_20_";"t"];

["_21_";"u"]; ["_22_";"v"]; ["_23_";"w"]; ["_24_";"x"]; ["_25_";"y"];

["_0_";"z"]

)

Posted

Cipher solution breaks when numbers appear in the message. I think using something like "{{1}}" instead of "_1_" should fix it. Just to be safe, the same convention should be used in my Rot13() too.

Posted

Good try...definitely doing it the hard way. I was looking for something that would work with upper and lower case letters and I'm not sure using obscure delimiters meets the criteria...unlikely, but someone might validly use {{1}} in a text.

Posted (edited)

I was looking for something that would work with upper and lower case letters

The Rot13() could be augmented with all of the uppercase substitutions. Trivial but tedious.

The similarly coded CaesarCipher() would need additional substitutions for upper case. Using "{{1}}} for "a" and {^1^} for "A" should keep the cases separate.

For another submission here's a recursive function that is limited to FileMaker's 10,000 nesting for head recursion. Thus 10,000 char limit. Handles upper and lower case.

/* Caesar_cf(text; offset) */

/* recursive function */

/* */

Let(

[

n = Length(text);

x = Code(Left(text;1));

yuo = Mod(x - 96 + offset; 26);

ylo = Mod(x - 64 + offset; 26)

];

Case(

n = 0; "";

Case(

x > (97+25); Char(x); // > z

x < (65); Char(x); // < A

(x > 90) and (x < 97); Char(x); // Z < x < a

x ≥ 97; If(yuo; Char(yuo + 96); "z"); // a-z

If(ylo; Char(ylo + 64); "Z") // A-Z

) &

Caesar_cf(Right(text;n - 1); offset)

))

Edited by Guest
Posted

For the sake of completeness, here is the brute force Substitute method handling upper and lowercase.

/* CeasarCipher(text; offset) */

/* */

Substitute(

Substitute(

text;

["a";"{{" & Mod(1 + offset;26) & "}}"]; ["b";"{{" & Mod(2 + offset;26) & "}}"]; ["c";"{{" & Mod(3 + offset;26) & "}}"];

["d";"{{" & Mod(4 + offset;26) & "}}"]; ["e";"{{" & Mod(5 + offset;26) & "}}"]; ["f";"{{" & Mod(6 + offset;26) & "}}"];

["g";"{{" & Mod(7 + offset;26) & "}}"]; ["h";"{{" & Mod(8 + offset;26) & "}}"]; ["i";"{{" & Mod(9 + offset;26) & "}}"];

["j";"{{" & Mod(10 + offset;26) & "}}"]; ["k";"{{" & Mod(11 + offset;26) & "}}"]; ["l";"{{" & Mod(12 + offset;26) & "}}"];

["m";"{{" & Mod(13 + offset;26) & "}}"]; ["n";"{{" & Mod(14 + offset;26) & "}}"];["o";"{{" & Mod(15 + offset;26) & "}}"];

["p";"{{" & Mod(16 + offset;26) & "}}"]; ["q";"{{" & Mod(17 + offset;26) & "}}"]; ["r";"{{" & Mod(18 + offset;26) & "}}"];

["s";"{{" & Mod(19 + offset;26) & "}}"]; ["t";"{{" & Mod(20 + offset;26) & "}}"]; ["u";"{{" & Mod(21 + offset;26) & "}}"];

["v";"{{" & Mod(22 + offset;26) & "}}"]; ["w";"{{" & Mod(23 + offset;26) & "}}"]; ["x";"{{" & Mod(24 + offset;26) & "}}"];

["y";"{{" & Mod(25 + offset;26) & "}}"]; ["z";"{{" & Mod(26 + offset;26) & "}}"];

["A";"{^" & Mod(1 + offset;26) & "^}"]; ["B";"{^" & Mod(2 + offset;26) & "^}"]; ["C";"{^" & Mod(3 + offset;26) & "^}"];

["D";"{^" & Mod(4 + offset;26) & "^}"]; ["E";"{^" & Mod(5 + offset;26) & "^}"]; ["F";"{^" & Mod(6 + offset;26) & "^}"];

["G";"{^" & Mod(7 + offset;26) & "^}"]; ["H";"{^" & Mod(8 + offset;26) & "^}"]; ["I";"{^" & Mod(9 + offset;26) & "^}"];

["J";"{^" & Mod(10 + offset;26) & "^}"]; ["K";"{^" & Mod(11 + offset;26) & "^}"]; ["L";"{^" & Mod(12 + offset;26) & "^}"];

["M";"{^" & Mod(13 + offset;26) & "^}"]; ["N";"{^" & Mod(14 + offset;26) & "^}"];["O";"{^" & Mod(15 + offset;26) & "^}"];

["P";"{^" & Mod(16 + offset;26) & "^}"]; ["Q";"{^" & Mod(17 + offset;26) & "^}"]; ["R";"{^" & Mod(18 + offset;26) & "^}"];

["S";"{^" & Mod(19 + offset;26) & "^}"]; ["T";"{^" & Mod(20 + offset;26) & "^}"]; ["U";"{^" & Mod(21 + offset;26) & "^}"];

["V";"{^" & Mod(22 + offset;26) & "^}"]; ["W";"{^" & Mod(23 + offset;26) & "^}"]; ["X";"{^" & Mod(24 + offset;26) & "^}"];

["Y";"{^" & Mod(25 + offset;26) & "^}"]; ["Z";"{^" & Mod(26 + offset;26) & "^}"]);

["{{1}}";"a"]; ["{{2}}";"b"]; ["{{3}}";"c"]; ["{{4}}";"d"]; ["{{5}}";"e"];

["{{6}}";"f"]; ["{{7}}";"g"]; ["{{8}}";"h"]; ["{{9}}";"i"]; ["{{10}}";"j"];

["{{11}}";"k"]; ["{{12}}";"l"]; ["{{13}}";"m"]; ["{{14}}";"n"];["{{15}}";"o"];

["{{16}}";"p"]; ["{{17}}";"q"]; ["{{18}}";"r"]; ["{{19}}";"s"]; ["{{20}}";"t"];

["{{21}}";"u"]; ["{{22}}";"v"]; ["{{23}}";"w"]; ["{{24}}";"x"]; ["{{25}}";"y"];

["{{0}}";"z"];

["{^1^}";"A"]; ["{^2^}";"B"]; ["{^3^}";"C"]; ["{^4^}";"D"]; ["{^5^}";"E"];

["{^6^}";"F"]; ["{^7^}";"G"]; ["{^8^}";"H"]; ["{^9^}";"I"]; ["{^10^}";"J"];

["{^11^}";"K"]; ["{^12^}";"L"]; ["{^13^}";"M"]; ["{^14^}";"N"];["{^15^}";"O"];

["{^16^}";"P"]; ["{^17^}";"Q"]; ["{^18^}";"R"]; ["{^19^}";"S"]; ["{^20^}";"T"];

["{^21^}";"U"]; ["{^22^}";"V"]; ["{^23^}";"W"]; ["{^24^}";"X"]; ["{^25^}";"Y"];

["{^0^}";"Z"]

)

Posted

What about something along this line ?

( still in progress for simplify and complete )

Substitute ( Substitute ( text

; [ Char ( 65 ) ; Char ( 1000 ) ]

; [ Char ( 66 ) ; Char ( 1001 ) ]

; [ Char ( 67 ) ; Char ( 1002 ) ]

; [ Char ( 68 ) ; Char ( 1003 ) ]

; [ Char ( 69 ) ; Char ( 1004 ) ]

; [ Char ( 70 ) ; Char ( 1005 ) ]

; [ Char ( 71 ) ; Char ( 1006 ) ]

; [ Char ( 72 ) ; Char ( 1007 ) ]

; [ Char ( 73 ) ; Char ( 1008 ) ]

; [ Char ( 74 ) ; Char ( 1009 ) ]

; [ Char ( 75 ) ; Char ( 1010 ) ]

; [ Char ( 76 ) ; Char ( 1011 ) ]

; [ Char ( 77 ) ; Char ( 1012 ) ]

; [ Char ( 78 ) ; Char ( 1013 ) ]

; [ Char ( 79 ) ; Char ( 1014 ) ]

; [ Char ( 80 ) ; Char ( 1015 ) ]

; [ Char ( 81 ) ; Char ( 1016 ) ]

; [ Char ( 82 ) ; Char ( 1017 ) ]

; [ Char ( 83 ) ; Char ( 1018 ) ]

; [ Char ( 84 ) ; Char ( 1019 ) ]

; [ Char ( 85 ) ; Char ( 1020 ) ]

; [ Char ( 86 ) ; Char ( 1021 ) ]

; [ Char ( 87 ) ; Char ( 1022 ) ]

; [ Char ( 88 ) ; Char ( 1023 ) ]

; [ Char ( 89 ) ; Char ( 1024 ) ]

; [ Char ( 90 ) ; Char ( 1025 ) ]

)

; [ Char ( 1000 ) ; Char ( 78 ) ]

; [ Char ( 1001 ) ; Char ( 79 ) ]

; [ Char ( 1002 ) ; Char ( 80 ) ]

; [ Char ( 1003 ) ; Char ( 81 ) ]

; [ Char ( 1004 ) ; Char ( 82 ) ]

; [ Char ( 1005 ) ; Char ( 83 ) ]

; [ Char ( 1006 ) ; Char ( 84 ) ]

; [ Char ( 1007 ) ; Char ( 85 ) ]

; [ Char ( 1008 ) ; Char ( 86 ) ]

; [ Char ( 1009 ) ; Char ( 87 ) ]

; [ Char ( 1010 ) ; Char ( 88 ) ]

; [ Char ( 1011 ) ; Char ( 89 ) ]

; [ Char ( 1012 ) ; Char ( 90 ) ]

; [ Char ( 1013 ) ; Char ( 65 ) ]

; [ Char ( 1014 ) ; Char ( 66 ) ]

; [ Char ( 1015 ) ; Char ( 67 ) ]

; [ Char ( 1016 ) ; Char ( 68 ) ]

; [ Char ( 1017 ) ; Char ( 69 ) ]

; [ Char ( 1018 ) ; Char ( 70 ) ]

; [ Char ( 1019 ) ; Char ( 71 ) ]

; [ Char ( 1020 ) ; Char ( 72 ) ]

; [ Char ( 1021 ) ; Char ( 73 ) ]

; [ Char ( 1022 ) ; Char ( 74 ) ]

; [ Char ( 1023 ) ; Char ( 75 ) ]

; [ Char ( 1024 ) ; Char ( 76 ) ]

; [ Char ( 1025 ) ; Char ( 77 ) ]

)

Posted

My vote is for a recursive CF.

/*

Rot13 ( text )

*/

Let(

c = Code ( Left ( text ;  1 ) ) ;

Case ( c ;

Case(

c > 64 and c <  91 ; Char ( Mod ( c - 52 ; 26 ) + 65 ) ;

c > 96 and c < 123 ; Char ( Mod ( c - 84 ; 26 ) + 97 ) ;

Char ( c )

) & Rot13 ( Right ( text ; Length ( text ) - 1 ) ) )

)

Posted

Here's mine:

Let([

var = Mod(var;26);

thisChar = Left(text;1);

num = Code(thisChar);

type = Case( (num ≥ 65 and num ≤ 90) ; "upper"; num ≥ 97 and num ≤ 122; "lower" ; "non") ;

rotted = num + Case( type = "non"; 0; var);

adjust = Case( type = "upper" and rotted > 90; rotted -26; type = "lower" and rotted > 122; rotted - 26; rotted);

newChar = Char(adjust);

newText = Right(text; Length(text)-1);

result = newChar & Case( Length(newText); Rot(newText; var))

];

result

)

This topic is 5249 days old. Please don't post here. Open a new topic instead.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.