开发者

Replace a list of characters in a string and do not override replaced characters

开发者 https://www.devze.com 2023-04-05 14:08 出处:网络
I\'m working on this decryption program for a hobby of mine: geocaching. The idea I have a base list of chars :

I'm working on this decryption program for a hobby of mine: geocaching.

The idea

I have a base list of chars :

[a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,0,1,2,3,4,5,6,7,8,9]

And in a windows form you can specify with which character each character should be replaced.

[A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,9,8,7,6,5,4,3,2,1,0]

So this would result in my string to decrypt being converted into uppercase.

example: the quick brown fox jumps over the lazy dog would result in THE QUICK BROWN FOX JUMPS OVER THE LAZY DOG

How I solved it

public static string DecodeWithKey(string source, string keyBase, string keyValue)
{
    StringBuilder sb = new StringBuilder(source);
    for (int i = 0; i < keyBase.Length; i++)
    {
        sb = sb.Replace(keyBase[i], keyValue[i]);
    }
    return sb.ToString();
}

Now this works fine for the above sample. But it completely fails when you start moving characters around.

The problem is in the order of things

So let's say this is my base again:

[a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,0,1,2,3,4,5,6,7,8,9]

And now I'm u开发者_开发知识库sing a bit more realistic values to be replaced:

[a,b,c,d,t,f,g,h,i,j,k,l,m,n,o,p,q,r,s,p,u,v,w,x,y,z,0,1,2,3,4,5,6,7,8,9]

Notice, I changed e with t and t with p.

The result: the quick brown fox jumps over the lazy dog becomes php quick brown fox jumps ovpr php lazy dog

As you can see in the it replaced it to tht and then to php. Which is obvious from my logic.

How can I prevent this? so that is shows pht and doesn't replace a character twice.

I hope I have explained it clearly.


Why don't you simply build the decoded string character by character rather than modifying a copy of the source in-place?

First, build a dictionary that matches each coded char to its decoded value

public static string DecodeWithKey(string source, Dictionary<char,char> decoder) 
{ 
    StringBuilder sb = new StringBuilder(source.Length); 
    for (int i = 0; i < source.Length; i++) 
    { 
        sb.Append( decoder[source[i]] ); // error management left out as an exercice
    } 
    return sb.ToString(); 
}

In response to Piotr comment, let's try to throw some LINQ into the game:

public static string DecodeWithKey(string source, Dictionary<char,char> decoder) 
{ 
    return String.Concat(from ch in source select decoder[ch]);
}


You can use regex replace to do what you want. Have a look at this question.

Convert your replacements to a dictionary, and then:

var regex = new Regex(String.Join("|",map.Keys));
var newStr = regex.Replace(str, m => map[m.Value]);
0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号