Bitwise OR for strings for large strings in C #

I have two lines (with 1 and 0) of the same length (<= 500) and would like to apply a logical OR to these lines.

How do I approach this. I am working with C #.

When I consider the obvious solution, read each char and apply OR | on them I have to deal with apx, 250,000 lines, each with a length of 500. this will kill my work.

Performance is my main concern.

Thanks in advance!

+5
source share
5 answers

This is the fastest way:

string x=""; string y=""; StringBuilder sb = new StringBuilder(x.Length); for (int i = 0; i < x.Length;i++ ) { sb.Append(x[i] == '1' || y[i] == '1' ? '1' : '0'); } string result = sb.ToString(); 
+4
source

Since it was mentioned that speed is a big factor, it would be better to use bitwise operations.

Look at the ASCII table:

  • The character '0' is 0x30 or 00110000 in binary format.
  • The character '1' is 0x31 or 00110001 in binary format.

Only the last bit of a character is different. Thus, we can confidently say that executing a bitwise OR on the characters themselves will lead to the creation of the correct character.

Another important thing we can do β€” to optimize speed β€” is to use a StringBuilder initialized to the original capacity of our string. Or even better: we can reuse StringBuilder for several operations, although we must ensure that StringBuilder has sufficient capacity.

Given these optimizations, we can make this method:

 string BinaryStringBitwiseOR(string a, string b, StringBuilder stringBuilder = null) { if (a.Length != b.Length) { throw new ArgumentException("The length of given string parameters didn't match"); } if (stringBuilder == null) { stringBuilder = new StringBuilder(a.Length); } else { stringBuilder.Clear().EnsureCapacity(a.Length); } for (int i = 0; i < a.Length; i++) { stringBuilder.Append((char)(a[i] | b[i])); } return stringBuilder.ToString(); } 

Note that this will work for all bit operations that you would like to perform in your lines, you only need to change the | .

+3
source

I have two lines (with 1 and 0) of the same length (<= 500) and will, for example, apply logical OR to these lines.

You can write a custom logical OR operator or a function that takes two characters as input and produces the result (for example, if at least one of the input characters "1" returns "1", otherwise it returns "0"). Apply this function to each character in your lines.

You can also look at this approach. First you need to convert each character to boolean (for example, β€œ1” matches true), perform an OR operation between two logical values, convert the result back to a β€œ0” or β€œ1” character, depending on whether the logical OR result was false or respectively, respectively. Then simply add each result of this operation to each other.

+2
source

I found this to be faster than all the solutions offered. It combines the response elements of @Gediminas and @Sakura, but uses a pre-initialized char[] , not StringBuilder .

Although StringBuilder effective in managing memory, each Append operation requires some token validation and performs more actions than just the index in the array.

 string x = ... string y = ... char[] c = new char[x.Length]; for (int i = 0; i < x.Length; i++) { c[i] = (char)(x[i] | y[i]); } string result = new string(c); 
+2
source

You can use the Linq query for zip and then aggregate the results:

 var a = "110010"; var b = "001110"; var result = a.Zip(b, (i, j) => i == '1' || j == '1' ? '1' : '0') .Select(i => i + "").Aggregate((i, j) => i + j); 

Basically, the Zip extension method takes two sequences and applies an action to each of the corresponding elements of the two sequences. Then I use Select "to translate from char to String and finally I set the results from a sequence of strings (from" 0 "and" 1 ") to the string.

+1
source

Source: https://habr.com/ru/post/1244517/


All Articles