2012-09-21 18 views
14

Mam maskę wyliczenia flagi (int) i muszę ją przekonwertować na ciąg reprezentujący dzień tygodnia.Zastosuj "maskę" do łańcucha

powiedzieć, jest to pełny ciąg i arbitralne maska ​​

strFullWeek = "MTWtFSs" 
strWeekMask = "0100110" 
----------------------- 
strResult = "-T--FS-" 

jaki sposób byś zaproponować uzyskuje strResult z całego tygodnia i maski strun?

UPDATE

to moja "cały kontekst" (VB.NET)

<Flags()> Public Enum Week 
    Monday = 1 
    Tuesday = 2 
    Wednesday = 4 
    Thursday = 8 
    Friday = 16 
    Saturday = 32 
    Sunday = 64 
End Enum 

Dim mondayOrSunday = Week.Monday Or Week.Sunday 
Dim strDays = "MTWtFSs" 

Dim strMondayOrSundayBinary = Convert.ToString(
    mondayOrSunday, 2).PadRight(7, CChar("0")) 

Dim charMondayOrSunday = strDays.Zip(
    strMondayOrSundayBinary, 
    Function(day, mask) If(mask = CChar("1"), day, CChar("-"))).ToArray() 

Dim strMondayOrSunday = New String(charMondayOrSunday) 

Console.WriteLine("{0} I see as {1}", 
        mondayOrSunday, 
        strMondayOrSunday) 
+0

Co Cię najbardziej niepokoi? Szybkość, łatwość konserwacji/czytelność, najmniejsze linie kodu? –

Odpowiedz

20

Jest rozsądnie schludny LINQ sposób:

var chars = strFullWeek.Zip(strWeekMask, (day, mask) => mask == '1' ? day : '-')) 
         .ToArray(); 
string text = new string(chars); 

Nie byłoby strasznie wydajny, ale może być wystarczająco dobry ...

EDYCJA: Dobra, zakładając, że jesteś zadowolony z kodu C# do enum vers jonowy

// TODO: Rename "Week" to comply with .NET naming conventions 
Week mask = Week.Monday | Week.Sunday; 
var chars = strFullWeek.Select((value, index) => (int) mask & (1 << index) != 0) 
               ? value : '-') 
         .ToArray(); 
string text = new string(chars); 
+0

Aby uzyskać 'strWeekMask' użyłem' Convert.ToString (myEnum, 2) '... może mógłbym użyć enum bezpośrednio? – serhio

+7

Tak więc * jest * użycie dla 'Zip()' ... – Laoujin

+0

@serhio: Tak, prawie na pewno. Daj nam pełny kontekst, a my będziemy mogli dać ci lepszą odpowiedź. –

3

Proszę bardzo:

var strFullWeek = "MTWtFSs"; 
var strWeekMask = "0100110"; 

var strFullWeekArray = strFullWeek.ToList(); 
var strWeekMaskArray = strWeekMask.ToList(); 

Console.WriteLine(string.Join(
    string.Empty, 
    strFullWeek.Select(c => (strWeekMaskArray[strFullWeekArray.IndexOf(c)] == '1') 
     ? c 
     : '-'))); 
2

Oto alternatywa jeśli szukasz czytelności:

string fullWeek = "MTWtFSs"; 
string weekMask = "0100110"; 

const char blankChar = '-'; 

int totalChars = fullWeek.Length; 

StringBuilder result = new StringBuilder(); 

for (int index = 0; index < totalChars; index++) 
{ 
    if (weekMask[index] == '1') 
    { 
     result.Append(fullWeek[index]); 
    } 
    else 
    { 
     result.Append(blankChar); 
    } 
} 

Console.WriteLine(result); 
5

My speedy rozwiązanie wykorzystuje StringBuilder. Pozwala na manipulowanie ciągiem w miejscu. Ale jeśli nie wywołasz tego kodu milion razy, nie zauważysz żadnej różnicy w prędkości w porównaniu do rozwiązań LINQ.

string strFullWeek = "MTWtFSs"; 
string strWeekMask = "0100110"; 

var sb = new StringBuilder(strFullWeek); 
for (int i = 0; i < strWeekMask.Length; i++) { 
    if (strWeekMask[i] == '0') { 
     sb[i] = '-'; 
    } 
} 
string result = sb.ToString(); 
1

Jestem spóźniony na imprezę; ale chciałem spróbować. Oto mój mniej chłodne podejście LINQ:

var result = new string(strFullWeek.Select((letter, index) 
         => strWeekMask[index] == '1' ? letter : '-').ToArray()); 
1

Jeśli chcesz użyć wyliczenie bezpośrednio, można zrobić coś takiego:

[Flags()] 
enum Week 
{ 
    Monday = 1, 
    Tuesday = 2, 
    Wednesday = 4, 
    Thursday = 8, 
    Friday = 16, 
    Saturday = 32, 
    Sunday = 64 
} 

const string strFullWeek = "MTWtFSs"; 

string GetMaskedWeek(Week days) 
{ 
    char[] result = new char[strFullWeek.Length]; 
    for (int i = 0; i < strFullWeek.Length; i++) 
    { 
     if ((((int)days >> i) & 1) != 0) 
      result[i] = strFullWeek.ToCharArray(i, 1)[0]; 
     else 
      result[i] = '-'; 
    } 
    return new string(result); 
} 

Albo w VB.NET:

<Flags()> Public Enum Week 
    Monday = 1 
    Tuesday = 2 
    Wednesday = 4 
    Thursday = 8 
    Friday = 16 
    Saturday = 32 
    Sunday = 64 
End Enum 

Dim strFullWeek As String = "MTWtFSs" 

Private Function GetMaskedWeek(ByVal days As Week) As String 
    Dim result(strFullWeek.Length) As Char 
    For i As Integer = 0 To strFullWeek.Length - 1 
     If ((days >> i) And 1) <> 0 Then 
      result(i) = strFullWeek.ToCharArray(i, 1)(0) 
     Else 
      result(i) = "-"c 
     End If 
    Next 
    Return New String(result) 
End Function 
+0

Czwartek = 8;) – serhio

+0

To jest tak naprawdę, co pierwotnie miałem, ale zaktualizowałem go tak, aby pasował do enum w pytaniu, które ma czwartek jako 16 :) –

Powiązane problemy