[Flags] Enum atributi C# da nimani anglatadi?

Vaqti-vaqti bilan men quyidagi kabi enumni ko'raman:

[Flags]
public enum Options 
{
    None    = 0,
    Option1 = 1,
    Option2 = 2,
    Option3 = 4,
    Option4 = 8
}

[Flags] atributi aynan nima qilishini tushunmayapman.

Kimda yaxshi tushuntirish yoki misol yuborishi mumkin?


person Brian Leahy    schedule 12.08.2008    source manba
comment
Shuni ham ta'kidlash joizki, qabul qilingan javobdan tashqari, VB.NET aslida talab [Bayroqlar] - hech bo'lmaganda .NET xodimlariga ko'ra: social.msdn.microsoft.com/forums/en-US/thread /   -  person Rushyo    schedule 30.07.2012
comment
E'tibor bering, bugungi kunda VBda talab qilinmaydi. Xulq-atvorni C# sifatida saqlang - faqat ToString() chiqishini o'zgartiradi. E'tibor bering, siz mantiqiy YOKI Enumning o'zida ham qilishingiz mumkin. Juda zo'r. Cat = 1, Dog = 2, CatAndDog = Cat || It.   -  person Chalky    schedule 04.08.2015
comment
@Chalky Siz CatAndDog = Cat | Dog (shartli o'rniga mantiqiy OR) degani, menimcha?   -  person DdW    schedule 12.09.2016
comment
@DdW, qisman to'g'ri: | ishlatilishi kerak, lekin | ikkilik OR deb ataladi. II mantiqiy OR (qisqa tutashuvga imkon beradi): Hech bo'lmaganda Microsoft-ga ko'ra;) msdn.microsoft.com/en-us/library/f355wky8.aspx   -  person Pieter21    schedule 01.04.2018


Javoblar (13)


[Flags] atributi sanab o'tiladigan qiymat bitta qiymatni emas, balki mumkin bo'lgan qiymatlar to'plamini ifodalaganda ishlatilishi kerak. Bunday to'plamlar ko'pincha bitli operatorlar bilan ishlatiladi, masalan:

var allowedColors = MyColor.Red | MyColor.Green | MyColor.Blue;

Shuni esda tutingki, [Flags] atributi o'z-o'zidan buni yoqmaydi - u faqat .ToString() usuli bilan chiroyli tasvirlashga imkon beradi:

enum Suits { Spades = 1, Clubs = 2, Diamonds = 4, Hearts = 8 }
[Flags] enum SuitsFlags { Spades = 1, Clubs = 2, Diamonds = 4, Hearts = 8 }

...

var str1 = (Suits.Spades | Suits.Diamonds).ToString();
           // "5"
var str2 = (SuitsFlags.Spades | SuitsFlags.Diamonds).ToString();
           // "Spades, Diamonds"

Shuni ham ta'kidlash kerakki, [Flags] avtomatik ravishda enum qiymatlarini ikkining kuchiga aylantirmaydi. Agar siz raqamli qiymatlarni o'tkazib yuborsangiz, raqam bit bo'yicha operatsiyalarda kutilgandek ishlamaydi, chunki sukut bo'yicha qiymatlar 0 dan boshlanadi va o'sadi.

Noto'g'ri deklaratsiya:

[Flags]
public enum MyColors
{
    Yellow,  // 0
    Green,   // 1
    Red,     // 2
    Blue     // 3
}

Agar shunday e'lon qilingan bo'lsa, qiymatlar Sariq = 0, Yashil = 1, Qizil = 2, Moviy = 3 bo'ladi. Bu uni bayroqlar sifatida foydasiz qiladi.

Mana to'g'ri deklaratsiyaga misol:

[Flags]
public enum MyColors
{
    Yellow = 1,
    Green = 2,
    Red = 4,
    Blue = 8
}

Mulkingizdagi aniq qiymatlarni olish uchun buni qilish mumkin:

if (myProperties.AllowedColors.HasFlag(MyColor.Yellow))
{
    // Yellow is allowed...
}

yoki .NET 4 dan oldin:

if((myProperties.AllowedColors & MyColor.Yellow) == MyColor.Yellow)
{
    // Yellow is allowed...
}

if((myProperties.AllowedColors & MyColor.Green) == MyColor.Green)
{
    // Green is allowed...
}    

Yopqoq ostida

Bu ishlaydi, chunki siz ro'yxatda ikkita kuch ishlatgansiz. Qopqoq ostida sizning hisob qiymatlaringiz ikkilik va nollarda shunday ko'rinadi:

 Yellow: 00000001
 Green:  00000010
 Red:    00000100
 Blue:   00001000

Xuddi shunday, AllowedColors xususiyatini ikkilik bitli OR | operatori yordamida Qizil, Yashil va Moviyga o‘rnatganingizdan so‘ng, AllowedColors quyidagicha ko‘rinadi:

myProperties.AllowedColors: 00001110

Shunday qilib, siz qiymatni olganingizda, aslida qiymatlar bo'yicha bit bo'yicha VA & bajarasiz:

myProperties.AllowedColors: 00001110
             MyColor.Green: 00000010
             -----------------------
                            00000010 // Hey, this is the same as MyColor.Green!

Yo'q = 0 qiymati

MSDN dan iqtibos keltirgan holda, ro'yxatingizda 0 dan foydalanish bo'yicha:

[Flags]
public enum MyColors
{
    None = 0,
    ....
}

Qiymati nolga teng bo'lgan bayroqning sanab o'tilgan doimiy nomi sifatida None dan foydalaning. Natija har doim nolga teng boʻlgani uchun bayroqni sinash uchun Bit boʻyicha AND operatsiyasida None sanab oʻtilgan konstantadan foydalana olmaysiz. Shu bilan birga, raqamli qiymat va qiymat oʻrtasida bit boʻyicha emas, balki mantiqiy taqqoslashni amalga oshirishingiz mumkin. Raqamli qiymatdagi har qanday bit o'rnatilgan yoki yo'qligini aniqlash uchun sanab o'tilmagan doimiy.

Bayroqlar atributi va undan foydalanish haqida batafsil ma'lumotni msdn va msdn da bayroqlarni loyihalash

person andynil    schedule 12.08.2008
comment
Bundan tashqari, Flags atributi aslida nima qilishini tushunmayapmanmi? Men o'zimning bayroqlar enum atributisiz aniq belgilash va foydalanishga qodirman. Bu faqat enum bayroqlar sifatida ishlatilishi mumkinligini ko'rsatish uchun ishlatiladimi? - person Oskar; 06.08.2009
comment
Bayroqlarning o'zi hech narsa qilmaydi. Bundan tashqari, C# o'z-o'zidan Bayroqlarni talab qilmaydi. Lekin sizning raqamingizning ToString ilovasi Bayroqlardan foydalanadi va Enum.IsDefined, Enum.Parse va hokazo. Bayroqlarni olib tashlashga harakat qiling va MyColor.Yellow | natijasiga qarang. MyColor.Red; busiz siz 5 ta olasiz, bayroqlar bilan siz sariq, qizil olasiz. Ramkaning ba'zi boshqa qismlari ham [Bayroqlar] dan foydalanadi (masalan, XML Serialization). - person Ruben; 17.08.2009
comment
Flags atributi ToString usulidan ko'ra ko'proq ta'sirga ega. Visual studio uni dizaynerda Enum dan foydalanganda hech bo'lmaganda ma'lum darajada ishlatadi. Mening savolimni bu yerda ko'ring: stackoverflow.com/q/15663166/1111886 - person Fr33dan; 27.03.2013
comment
Men A = 1 ‹‹ 0, B = 1 ‹‹ 1, C = 1 ‹‹ 2 shaklidagi konstantalardan foydalanishni afzal ko'raman ... O'qish, tushunish, vizual tekshirish va o'zgartirish ancha oson. - person Nick Westgate; 09.04.2013
comment
.HasFlag (Enum bayrog'i) usuli Enum tipidagi parametrni oladi, shuning uchun qiymat turi ishlash uchun yomon bo'lgan qutiga joylashtirilishi kerak - person Aleksei Chepovoi; 04.05.2013
comment
@AlekseiChepovoi Enum ValueType sinfidan kelib chiqadi, bu int, float va boshqalar bilan bir xil tarzda struct sifatida qaralishini anglatadi. - person borrrden; 24.06.2013
comment
@borrrden, biz Enum sinfidan (HasFlag usulini belgilaydigan sinf) o'tganimizda, men olganimdek, u mos yozuvlar orqali o'tadi. Men buni Jeffri Rixterning CLR-da C# uchinchi nashri, Enums va Bit Flags bo'limi orqali o'qib chiqdim. - person Aleksei Chepovoi; 27.06.2013
comment
@AlekseiChepovoi Menda ham o'sha kitob bor, shuning uchun uni tekshirib ko'raman. Bu men C# haqida bilgan hamma narsaga qarshi uchib ketganga o'xshaydi. Men topa oladigan har bir maqolada aytilishicha, enumlar to'pga ajratilmagan qiymat ob'ektlari hisoblanadi. - person borrrden; 27.06.2013
comment
@borrrden, jahannam ha! Men buni topdim: msdn.microsoft.com/en-us/library/ system.enum.aspx - Izohlar qismiga qarang: Enum .NET Frameworkdagi barcha sanablar uchun asosiy sinfdir. va ro'yxatga olish Enumdan aniq meros bo'lmaydi; meros munosabatlari kompilyator tomonidan bevosita boshqariladi. Shunday qilib, siz yozganingizda: public enum bla bla bla - bu qiymat turi. Biroq, HasFlag usuli sizdan unga sinf bo'lgan System.Enum misolini berishingizni xohlaydi (mos yozuvlar turi :) - person Aleksei Chepovoi; 28.06.2013
comment
Enum.IsDefined FlagsAttribute ni hisobga olmaydi. Quyidagi atributlardan hech biri to'g'ri kelmaydi: Sariq | Yashil, sariq, yashil, 3 - person TheXenocide; 07.12.2013
comment
Agar ko'k = 2 va yashil = 3 bo'lsa, sizning misolingiz Bayroqni idrok etishdan ko'proq ma'noga ega bo'ladi, chunki yashil rang sariq va ko'kning birikmasidir. - person MikeT; 11.06.2015
comment
Agar bayroqni ro'yxatga olishdan chiqarib tashlamoqchi bo'lsangiz, C# da ^ bo'lgan xor dan foydalaning. Shunday qilib, agar sizda myProperties.AllowedColors = MyColor.Red | MyColor.Green | MyColor.Blue; bo'lsa. Siz qila olasiz: myProperties.AllowedColors = myProperties.AllowedColors ^ MyColor.Blue //myProperties.AllowedColors == MyColor.Red | Mycolor.Green - person Josh Noe; 10.02.2018
comment
Men 10 nimani anglatishini qidirdim... ba'zi sinovlardan so'ng bu qiymat 2 va 8 yoki Green | Blue qiymatiga mos keladi. Shuningdek, Yellow = 1, Green = 2,... 8 qiymatlari 9 (8+1) yoki 11 (8+2+1) o'zgaruvchan ko'rinishga (‹‹) nisbatan nimani anglatishini oson tushunishga yordam beradi. - person Jaider; 26.05.2021

Buni ham qilishingiz mumkin

[Flags]
public enum MyEnum
{
    None   = 0,
    First  = 1 << 0,
    Second = 1 << 1,
    Third  = 1 << 2,
    Fourth = 1 << 3
}

Men 4,8,16,32 va hokazolarni yozishdan ko'ra bitni o'zgartirishni oson deb bilaman. Bu sizning kodingizga ta'sir qilmaydi, chunki hammasi kompilyatsiya vaqtida amalga oshiriladi

person Orion Edwards    schedule 12.08.2008
comment
Bu yorliqlar haqida menga yoqmaydigan yagona narsa, agar siz ushbu enumlarni ma'lumotlar bazasida ints sifatida saqlasangiz. Keyin ma'lumotlarni tahlil qilishda qaysi qiymatlar qaysi raqamga to'g'ri kelishini aniqlash uchun kalkulyatorni bir necha marta olish kerak. - person JeremyWeir; 14.05.2012
comment
@JeremyWeir 1, 2 , 4, 8, 16, ... dan qanday farq qilishini tushuntirib bera olasizmi? Shuningdek, Windows 7 kalkulyatorida siz bosishingiz mumkin bo'lgan bitlar mavjud. - person Silvermind; 27.05.2012
comment
Men shuni aytmoqchimanki, men manba kodida to'liq intga ega bo'lishni afzal ko'raman. Agar mening ma'lumotlar bazasida MyEnum deb nomlangan jadvalda raqamlardan birining qiymatini saqlaydigan ustun bo'lsa va yozuvda 131,072 bo'lsa, bu 1 qiymatiga ega bo'lgan enumga mos kelishini aniqlash uchun kalkulyatorimdan chiqishim kerak bo'ladi. ‹‹17. Manbada yozilgan 131,072 qiymatini ko'rishdan farqli o'laroq. - person JeremyWeir; 29.05.2012
comment
Bularning barchasi kompilyatsiya vaqtida amalga oshiriladi, bu turdagi sharhlar ba'zilar uchun qiziqarli bo'lishi mumkin, lekin men buni asabiylashtiraman, chunki bu ish vaqtidagi 20 bit-shiftlar ishlashga har qanday o'lchovli ta'sir ko'rsatishini anglatadi. Protsessorlar bit almashinuvida juda yaxshi, enumlar a'zolarning ixtiyoriy soniga ega bo'lmaydi va bu baribir 32 yoki 64 dan ortiq element uchun ishlamaydi. Ishlash muammosi sifatida unchalik muhim emas. - person jwg; 14.02.2013
comment
@jwg Qabul qilaman, bu ish vaqtining ishlashi haqida haddan tashqari tashvishlanish ahmoqlik, lekin baribir, bu siz enum ishlatadigan har qanday joyda bitshiftlarni kiritmasligini bilish yoqimli deb o'ylayman. Ishlash bilan bog'liq bo'lgan narsadan ko'ra ko'proq "bu chiroyli" narsa - person Orion Edwards; 15.02.2013
comment
@JeremyWeir - bayroq sanab qiymatida bir nechta bitlar o'rnatiladi. Shunday qilib, sizning ma'lumotlarni tahlil qilish usulingiz noto'g'ri. Butun qiymatingizni ikkilik tizimda ifodalash uchun protsedurani bajaring. 131,072 [D] = 0000 0000 0000 0001 0000 0000 0000 0000 [B] [32].. 17-bit to'plami bilan 1‹‹17 bilan tayinlangan enum qiymatini osongina aniqlash mumkin. 0110 0011 0011 0101 0101 0011 0101 1011 [b] [32] .. enum qiymatlari 1‹‹31, 1‹‹30, 1‹‹26, 1‹‹26 va hokazolarni belgilash mumkin. umuman kalkulyatorning yordami .. ikkilik vakilni olmasdan aniqlay olishingizga shubha qilaman. - person Brett Caswell; 19.03.2013
comment
Bundan tashqari, siz to'g'ridan-to'g'ri raqamlardan emas, balki oldingi enum qiymatlaridan, ya'ni Third = 1 << 2 o'rniga Third = Second << 1 o'zgartirishingiz mumkin -- quyida batafsil tavsifga qarang. - person drzaus; 16.05.2013
comment
Bu menga yoqadi, lekin siz asosiy enum turining yuqori chegaralariga kirganingizdan so'ng, kompilyator 1 << 31 == -2147483648, 1 << 32 == 1, 1 << 33 == 2 va hokazo kabi bit o'zgarishlaridan ogohlantirmaydi. Aksincha, agar siz int tipidagi enum uchun ThirtySecond = 2147483648 deb aytsangiz, kompilyator xatoga yo'l qo'yadi. - person aaaantoine; 04.06.2014
comment
C# 7 bilan yangi bo'lgan yana bir variantni qo'shish uchun siz 0b1, 0b10 va boshqalardan foydalanishingiz mumkin (yoki agar sizga hamma narsa to'g'ri kelishini yoqtirsangiz 0b00000001!) - person Graham Wager; 15.03.2017

Javoblarni birlashtirish https://stackoverflow.com/a/8462/1037948 (bit-shifting orqali deklaratsiya) va https://stackoverflow.com/a/9117/1037948 (deklaratsiyadagi kombinatsiyalardan foydalangan holda) foydalanish o'rniga oldingi qiymatlarni bit-shift qilishingiz mumkin. raqamlar. Buni tavsiya qilish shart emas, balki faqat ishora qilishingiz mumkin.

Dan ko'ra:

[Flags]
public enum Options : byte
{
    None    = 0,
    One     = 1 << 0,   // 1
    Two     = 1 << 1,   // 2
    Three   = 1 << 2,   // 4
    Four    = 1 << 3,   // 8

    // combinations
    OneAndTwo = One | Two,
    OneTwoAndThree = One | Two | Three,
}

Siz e'lon qilishingiz mumkin

[Flags]
public enum Options : byte
{
    None    = 0,
    One     = 1 << 0,       // 1
    // now that value 1 is available, start shifting from there
    Two     = One << 1,     // 2
    Three   = Two << 1,     // 4
    Four    = Three << 1,   // 8

    // same combinations
    OneAndTwo = One | Two,
    OneTwoAndThree = One | Two | Three,
}

LinqPad bilan tasdiqlanmoqda:

foreach(var e in Enum.GetValues(typeof(Options))) {
    string.Format("{0} = {1}", e.ToString(), (byte)e).Dump();
}

Natijalar:

None = 0
One = 1
Two = 2
OneAndTwo = 3
Three = 4
OneTwoAndThree = 7
Four = 8
person drzaus    schedule 16.05.2013
comment
Kombinatsiyalar yaxshi tavsiya, lekin oʻylaymanki, zanjirlangan bit-shift ikki = Bitta ‹‹ 1, Uch = Bitta ‹‹ 1 va boshqalar kabi nusxa koʻchirish va joylashtirish xatolariga moyil boʻladi... 1 ‹‹ n shakli xavfsizroq va niyat aniqroq. - person Rupert Rawnsley; 20.03.2014
comment
@RupertRawnsley mening javobimdan iqtibos keltirish uchun: › Buni tavsiya qilish shart emas, lekin shuni ta'kidlash kerakki - person drzaus; 20.03.2014

Deklaratsiya va potentsial foydalanishni ko'rsatadigan misol uchun quyidagini ko'ring:

namespace Flags
{
    class Program
    {
        [Flags]
        public enum MyFlags : short
        {
            Foo = 0x1,
            Bar = 0x2,
            Baz = 0x4
        }

        static void Main(string[] args)
        {
            MyFlags fooBar = MyFlags.Foo | MyFlags.Bar;

            if ((fooBar & MyFlags.Foo) == MyFlags.Foo)
            {
                Console.WriteLine("Item has Foo flag set");
            }
        }
    }
}
person OJ.    schedule 12.08.2008
comment
Bu misol [Bayroqlar] dan tashqarida qoldirsangiz ham ishlaydi. Bu men o'rganmoqchi bo'lgan [Bayroqlar] qismi. - person gbarry; 07.08.2019

Qabul qilingan javobni kengaytirish uchun C#7 da enum bayroqlari ikkilik harflar yordamida yozilishi mumkin:

[Flags]
public enum MyColors
{
    None   = 0b0000,
    Yellow = 0b0001,
    Green  = 0b0010,
    Red    = 0b0100,
    Blue   = 0b1000
}

Menimcha, bu tasvir bayroqlarningqopqoq ostida qanday ishlashini aniq ko'rsatib beradi.

person Thorkil Holm-Jacobsen    schedule 20.07.2017
comment
C# 7.2 da bu etakchi ajratuvchi! 0b_0100 - person Vincenzo Petronio; 26.10.2019

Men yaqinda so'radim shunga o'xshash narsa haqida.

Agar siz bayroqlardan foydalansangiz, mavjud bayroqlarni tekshirishni osonlashtirish uchun enumlarga kengaytma usulini qo'shishingiz mumkin (batafsil ma'lumot uchun postga qarang)

Bu sizga quyidagilarga imkon beradi:

[Flags]
public enum PossibleOptions : byte
{
    None = 0,
    OptionOne = 1,
    OptionTwo = 2,
    OptionThree = 4,
    OptionFour = 8,

    //combinations can be in the enum too
    OptionOneAndTwo = OptionOne | OptionTwo,
    OptionOneTwoAndThree = OptionOne | OptionTwo | OptionThree,
    ...
}

Keyin shunday qilishingiz mumkin:

PossibleOptions opt = PossibleOptions.OptionOneTwoAndThree 

if( opt.IsSet( PossibleOptions.OptionOne ) ) {
    //optionOne is one of those set
}

Men buni o'qishni kiritilgan bayroqlarni tekshirishning ko'p usullaridan ko'ra osonroq deb bilaman.

person Keith    schedule 12.08.2008
comment
IsSet men o'ylagan kengaytma usulimi? - person Robert MacLean; 02.06.2009
comment
Ha - batafsil ma'lumot uchun men bog'laydigan boshqa savolni o'qing: stackoverflow.com/questions/7244 - person Keith; 02.06.2009
comment
.NET 4 sanablarga HasFlag usulini qo'shadi, shuning uchun siz o'zingizning kengaytmalaringizni yozmasdan opt.HasFlag( PossibleOptions.OptionOne ) ni bajarishingiz mumkin - person Orion Edwards; 20.07.2010
comment
E'tibor bering, HasFlag bit bo'yicha operatsiyalarni bajarishdan ko'ra juda sekinroq. - person Wai Ha Lee; 12.09.2018
comment
@WaiHaLee Expression yordamida tez versiyaga kompilyatsiya qilingan CodeJam.EnumHelper.IsFlagSet kengaytmasi usulidan foydalanishingiz mumkin: github.com/rsdn/CodeJam/wiki/M_CodeJam_EnumHelper_IsFlagSet__1 - person NN_; 29.04.2019

Bayroqlar bilan ishlashda men ko'pincha qo'shimcha None va All elementlarni e'lon qilaman. Bu barcha bayroqlar o'rnatilganligini yoki hech qanday bayroq o'rnatilmaganligini tekshirish uchun foydalidir.

[Flags] 
enum SuitsFlags { 

    None =     0,

    Spades =   1 << 0, 
    Clubs =    1 << 1, 
    Diamonds = 1 << 2, 
    Hearts =   1 << 3,

    All =      ~(~0 << 4)

}

Foydalanish:

Spades | Clubs | Diamonds | Hearts == All  // true
Spades & Clubs == None  // true


Yangilanish 2019-10:

C# 7.0 dan boshlab siz o'qish uchun intuitiv bo'lgan ikkilik harflardan foydalanishingiz mumkin:

[Flags] 
enum SuitsFlags { 

    None =     0b0000,

    Spades =   0b0001, 
    Clubs =    0b0010, 
    Diamonds = 0b0100, 
    Hearts =   0b1000,

    All =      0b1111

}
person Jpsy    schedule 23.10.2018
comment
Ha, bu sahifadagi barcha javoblarni birlashtirib, men hozir buni muntazam ravishda ishlataman, lekin yetakchi ajratuvchi 0b_1111 bilan - person Marcelo Scofano Diniz; 03.08.2020

@Nidonocu

Mavjud qiymatlar to'plamiga boshqa bayroq qo'shish uchun OR tayinlash operatoridan foydalaning.

Mode = Mode.Read;
//Add Mode.Write
Mode |= Mode.Write;
Assert.True(((Mode & Mode.Write) == Mode.Write)
  && ((Mode & Mode.Read) == Mode.Read)));
person steve_c    schedule 12.08.2008

Mode.Write qo'shish uchun:

Mode = Mode | Mode.Write;
person David Wengier    schedule 12.08.2008

Menga if ((x & y) == y)... konstruktsiyasi haqida haddan tashqari batafsil gap bor, ayniqsa, x VA y ikkala bayroqlar birikmasi boʻlsa va siz faqatgina bir-birini oʻzaro bogʻliqlik bor yoki yoʻqligini bilishni istasangiz.

Bunday holda, faqat bitmask qo'yganingizdan so'ng noldan farqli qiymat[1] bo'lsani bilishingiz kerak.

[1] Jaimening sharhiga qarang. Agar biz haqiqiy bitmasking boʻlsak, natija ijobiy ekanligini tekshirishimiz kifoya qiladi. Ammo enumlar [Flags] atributi bilan birlashganda g'alati, hatto salbiy bo'lishi mumkin. , > 0 emas, balki != 0 uchun kodlash himoyaviydir.

@andnil sozlamalari asosida yaratilmoqda...

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace BitFlagPlay
{
    class Program
    {
        [Flags]
        public enum MyColor
        {
            Yellow = 0x01,
            Green = 0x02,
            Red = 0x04,
            Blue = 0x08
        }

        static void Main(string[] args)
        {
            var myColor = MyColor.Yellow | MyColor.Blue;
            var acceptableColors = MyColor.Yellow | MyColor.Red;

            Console.WriteLine((myColor & MyColor.Blue) != 0);     // True
            Console.WriteLine((myColor & MyColor.Red) != 0);      // False                
            Console.WriteLine((myColor & acceptableColors) != 0); // True
            // ... though only Yellow is shared.

            Console.WriteLine((myColor & MyColor.Green) != 0);    // Wait a minute... ;^D

            Console.Read();
        }
    }
}
person ruffin    schedule 01.05.2013
comment
Enum imzolangan turga asoslangan bo'lishi mumkin, shuning uchun siz ›0 o'rniga != 0 dan foydalanishingiz kerak. - person raven; 16.08.2013
comment
@JaimePardos -- Bu misolda qilganimdek, biz ularga halol baytlarni saqlasak, salbiy tushunchasi yo'q. Faqat 0 dan 255 gacha. MSDN ogohlantiradi, agar shunday bo'lsa, ehtiyot bo'ling. siz manfiy raqamni bayroq sanab o'tilgan doimiy sifatida belgilaysiz, chunki ... [bu] kodingizni chalkashtirib yuborishi va kodlash xatolarini rag'batlantirishi mumkin. Salbiy bit flaglar nuqtai nazaridan o'ylash g'alati! ;^) Yana birozdan keyin tahrir qilaman. Lekin siz haqsiz, agar biz enum da salbiy qiymatlardan foydalansak, != 0 ni tekshirishimiz kerak bo'ladi. - person ruffin; 16.08.2013

Bayroqlar sizning ro'yxatingizda bitmaskingdan foydalanishga imkon beradi. Bu sanab o'tilgan qiymatlarni birlashtirishga imkon beradi, shu bilan birga qaysilari ko'rsatilgan.

[Flags]
public enum DashboardItemPresentationProperties : long
{
    None = 0,
    HideCollapse = 1,
    HideDelete = 2,
    HideEdit = 4,
    HideOpenInNewWindow = 8,
    HideResetSource = 16,
    HideMenu = 32
}
person Jay Mooney    schedule 12.08.2008
comment
Bu noto'g'ri, enum Flags sifatida belgilanmagan bo'lsa ham, bitmaskingdan foydalanishingiz mumkin. - person Shadow; 01.11.2020

Agar kimdir bu stsenariyni allaqachon payqagan bo'lsa, uzr so'raymiz. Ko'zguda ko'rishimiz mumkin bo'lgan bayroqlarning mukammal namunasi. Ha Bituvchi bayroqlar ENUM .

[System.Flags]
[System.Runtime.InteropServices.ComVisible(true)]
[System.Serializable]
public enum BindingFlags

Foydalanish

// BindingFlags.InvokeMethod
// Call a static method.
Type t = typeof (TestClass);

Console.WriteLine();
Console.WriteLine("Invoking a static method.");
Console.WriteLine("-------------------------");
t.InvokeMember ("SayHello", BindingFlags.InvokeMethod | BindingFlags.Public | 
    BindingFlags.Static, null, null, new object [] {});
person kbvishnu    schedule 27.01.2020

  • Agar sanab o'tiladigan qiymat enum a'zolari to'plamini bildirsa, bayroqlar qo'llaniladi.

  • bu yerda biz bitli operatorlardan foydalanamiz, | va &

  • Misol

                 [Flags]
                 public enum Sides { Left=0, Right=1, Top=2, Bottom=3 }
    
                 Sides leftRight = Sides.Left | Sides.Right;
                 Console.WriteLine (leftRight);//Left, Right
    
                 string stringValue = leftRight.ToString();
                 Console.WriteLine (stringValue);//Left, Right
    
                 Sides s = Sides.Left;
                 s |= Sides.Right;
                 Console.WriteLine (s);//Left, Right
    
                 s ^= Sides.Right; // Toggles Sides.Right
                 Console.WriteLine (s); //Left
    
person Mukesh Pareek    schedule 11.11.2020
comment
Sizning misolingiz noto'g'ri (va u da'vo qilgan natijani keltirmaydi), chunki Flags dan to'g'ri foydalanish sizning enum qiymatlaringiz o'ziga xos bitlarga ega bo'lishini talab qiladi. Va kamida bitta to'plam bo'lishi kerak (agar siz None kabi psevdo qiymat bo'lmasa). Sizning raqamingiz kabi bo'lishi kerak ` public enum Sides { Left=1, Right=2, Top=4, Bottom=8 } ` - person Jakob; 18.11.2020