inicializace Direct pole s konstantní hodnotou

hlasů
43

Kdykoliv si přidělit nové pole v jazyce C # s

new T[length]

položky pole jsou nastaveny na výchozí T. To je nullpro případ, že Tje referenční typ nebo výsledek výchozí konstruktoru T, pokud Tje hodnota typu.

V mém případě chci inicializaci Int32pole s hodnotou -1:

var myArray = new int[100];
for (int i=0; i<myArray.Length; i++) { myArray[i] = -1; }

Takže po paměti je vyhrazeno pro pole, CLR smyčky přes nově přidělené paměti a nastaví všechny položky na výchozí (INT) = 0. Po že můj kód nastaví všechny položky -1.

To dělá inicializace nadbytečná. Má JIT to zjistí a zanedbává inicializaci na 0, a pokud ne, je tu způsob, jak přímo inicializovat část paměti s vlastní hodnotou?

S odvoláním na inicializaci # Array C - s jinou než výchozí hodnotu , s použitím Enumerable.Repeat(value, length).ToArray()není volba, protože Enumerable.ToArraypřiděluje nové pole a zkopíruje hodnoty na něj později.

Položena 16/03/2009 v 00:37
zdroj uživatelem
V jiných jazycích...                            


5 odpovědí

hlasů
33

Není to zbytečná.

Předpokládejme, že je vyvolána výjimka během inicializace smyčky. V případě, že CLR není nejprve vymazat paměť, měli byste být schopni „vidět“ originální neinicializované paměti, což je velmi špatný nápad, a to zejména z bezpečnostního hlediska. To je důvod, proč CLR zaručuje, že každý nově alokovaná paměť se otřel na 0 bitový vzor.

Stejný argument platí i pro pole v objektu, mimochodem.

Myslím, že v obou případech je CLR mohl ověřit, že nebudete dělat pole viditelné jinde před dokončením inicializace, ale je to složitější kontrola, aby se zabránilo velmi jednoduchá „tuto oblast vymazání paměti“.

Odpovězeno 16/03/2009 v 00:42
zdroj uživatelem

hlasů
26

Podobně jako Dan odpověď, ale bez potřeby použití ve sbírkách:

int[] myArray = Enumerable.Repeat(-1, 100).ToArray();
Odpovězeno 29/09/2009 v 18:33
zdroj uživatelem

hlasů
10

Pokud si koupíte do polí považovány spíše škodí , pak se vaše otázka by byla diskutabilní, jak byste napsat:

var myArray = new List<int>(Enumerable.Repeat(-1, 100));
Odpovězeno 16/03/2009 v 01:08
zdroj uživatelem

hlasů
3

Velmi pochybuji, že SVT bude optimalizovat pryč výchozí sadu pro tento scénář. Důvodem je, že to bude pozorovatelný rozdíl. Vezměme si následující mírně změněnou situaci.

obj.myArray = new int[100];
for (int i=0; i<myArray.Length; i++) { obj.myArray[i] = -1; }

Je zcela možné, že smyčka hodit. Alespoň, že to asi není možné, aby JIT dokázat, tomu tak není. Pokud by se mu hodit a CLR nebyl výchozí inicializaci paměti, výsledkem by bylo pozorovatelné, pokud jste ještě odkaz na obj.

Odpovězeno 16/03/2009 v 00:44
zdroj uživatelem

hlasů
0

Doporučuji používat Array.Filljako velmi úsečně způsob, jak naplnit pole s počáteční hodnoty:

bool[] isPrime = new bool[MaxNum];
Array.Fill(isPrime, true);

To inicializuje všechny hodnoty v isPrimepoli se true.

Odpovězeno 08/01/2019 v 13:03
zdroj uživatelem

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more