Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Общие вопросы по .NET и C# > Структура с массивом внутри


Автор: LamerTM 27.9.2009, 20:35
Как сделать структуру с индексируемыми полями. Ну или ее аналог. 


Например, структура должна содержать массив других структур.

В делфи это пишется так:

Код

rec1 = record
  a: double;
  b: double;
end;

rec = record
  arr: array[0..9] of rec1;
end;

Массив arr получается статическим. Находится в самой структуре ("записи" по-паскалевски). К его элементам можно обращаться в цикле перебирая индекс. Есть огромный массив из таких rec, из-за чего, как мне кажется, выгоднее чтобы массив arr находился весь в структуре, а не чтобы она содержала ссылку на динамический массив.

Как делают такие вещи на C#? (насколько я понимаю, в C# массив всегда является ссылкой)

Автор: Экскалупатор 28.9.2009, 01:27
да в общем все тривиально:
Код

public struct students 
            {
                public string Name;
                public string Group_number;
                public int[] Point;
                public double sr_ball;

        public students (string stud_name, string stud_group, int[] stud_point)
            {
                Name = stud_name;
                Group_number = stud_group;
                Point = stud_point;
                int sr=0;
                foreach (int a in Point)
                    {
                        sr+=a;
                    }
                sr_ball = sr / Point.Length;
            }
            }



делал такую структуру для задания в контрольной, тут типа есть структура, содержащая данные о студенте, и в этой структуре есть массив оценок этого студента, если надо то можно объявить этот массив статическим. ну соответственно есть вместо 
public int[] Point;
написать 
public MyStruct[] Point;
то получим массив структур. я думаю принцип должен быть понятен.

Автор: LamerTM 28.9.2009, 09:08
Да нет, тут немного не так. В структуре содержится только ссылка на массив, а не весь он сам. Похоже, как я хочу, в C# так сделать в принципе нельзя.
Единственный вариант, что я вижу, это в моём случае написать наподобие такого:

Код

    unsafe public struct Rec
    {
        public fixed double Arr1[10];
        public fixed double Arr2[10];
    }


Где Arr1 хранят первое поле из записи, а Arr2 - второе. Ну или в один массив их поместить можно. Короче, структуру фактически придется организовывать вручную.

Может кто другие варианты знает?

Автор: diadiavova 28.9.2009, 09:18
LamerTM, лично я не понял что ты хочешь сделать. Приведи пример, как должна работать твоя структура.

Добавлено через 7 минут и 8 секунд
И кстати, об этом ты знаешь?
http://msdn.microsoft.com/ru-ru/library/2yd9wwz4.aspx

Добавлено через 8 минут и 3 секунды
А об этом?
http://msdn.microsoft.com/ru-ru/library/2s05feca.aspx

Автор: LamerTM 28.9.2009, 09:45
Есть структура Rec1, буквально такая:

Код

    public struct Rec1
    {
        public double a;
        public double b;
    }


Хочется структуру Rec, которая содержит 2 массива из структур Rec1. Массивы фиксированной длины, по 10 элементов. Сткруктура должна содержать в себе весь массив, а не только ссылку на него.
Потом я создам большой массив из Rec, куда будет загружен файл.

Можно сделать аналог:

Код

public struct Rec
    {
        public Rec1 A0;
        public Rec1 A1;
        public Rec1 A2;
        <...>
        public Rec1 A9;

        public Rec1 B0;
        public Rec1 B1;
        public Rec1 B2;
        <...>
        public Rec1 B9;
    }

Вот хочется чтобы было не так, а через массивы. Тогда эти поля можно было бы перебирать по индексу.

Автор: diadiavova 28.9.2009, 10:01
Цитата(LamerTM @  28.9.2009,  10:45 Найти цитируемый пост)
Хочется структуру Rec, которая содержит 2 массива из структур Rec1. Массивы фиксированной длины, по 10 элементов.

Здесь не вижу проблем.

Цитата(LamerTM @  28.9.2009,  10:45 Найти цитируемый пост)
Сткруктура должна содержать в себе весь массив, а не только ссылку на него.

Массив - ссылочный объект и структура его не может содержать, только ссылку. Другой вопрос: "А какое вообще в данном случае имеет значение, как организована память структуры?". Допустим, то что тебе надо возможно. Какие выгоды ты собираешься из этого извлечь? Что такого можно сделать со структурой, когда она "содержит массив, а не ссылку"?

Цитата(LamerTM @  28.9.2009,  10:45 Найти цитируемый пост)
Тогда эти поля можно было бы перебирать по индексу. 

Ну это и сейчас возможно, просто добавь метод, который по индексу будет нужное поле возвращать.

Автор: LamerTM 28.9.2009, 10:29
Цитата(diadiavova @  28.9.2009,  10:01 Найти цитируемый пост)
 Другой вопрос: "А какое вообще в данном случае имеет значение, как организована память структуры?"

Я всегда так делал на делфи, и поэтому чисто по привычке хотел реализовать именно так.

Я собираюсь иметь большой массив таких структур, куда будет заргужен файл.
Если структура содержит ссылки на массив, то это приводит к большему расходу памяти, т.к. нужно отводить память под ссылку. Но сейчас память для меня не очень важна, эта ссылка много не займет. Меня пугает что если я выделю массив в 100 000 структур Rec, то потом надо будет выделить еще 200 000 массивов по 10 структур Rec1. Не будет ли на этой операции грандиозного тормоза, расхода памяти и так далее. Да и выглядит кривовато это. Т.к. тестить лень, то хочется сделать сразу заведомо без этих операций.

Надо будет попробовать сделать по-разному и сравнить. Может и не стоит оно того.

Автор: diadiavova 28.9.2009, 10:40
Об экономии памяти на ссылках слышу(точнее читаю) впервые. Возможно я чего-то не догоняю, но ИМХО, ты не туда копаешь.

Автор: PashaPash 28.9.2009, 11:23
LamerTM, http://msdn.microsoft.com/ru-ru/library/zycewsya.aspx. Но в целом - не советую. Выделение одного здорового буффера на 100 000 структур с fixed-массивами - это почти гарантированно OutOfMemoryException. Лучше куча мелких объектов, чем один большой.

Автор: mr.DUDA 28.9.2009, 17:10
Есть ещё такая штука в дотнете как Large Object Heap. Если пытаться пихать все свои мелкие объекты имба-массивы то можно упереться в OutOfMemoryException, как справедливо заметил PashaPash, т.к. аллокации даже 30-50кб будут упираться в полностью занятый LOH (даже при наличии свободной памяти и файла подкачки ещё на 4-10 гигов).

Автор: Scatman 29.9.2009, 13:41
а так и делай хоть какой массив
Код

class Depot
    {
        public int[] O1;   
        public int[] O2;

   }
    
    class Config
    {

        public Depot[] filial;
    }

Автор: LamerTM 3.10.2009, 17:36
Цитата(diadiavova @  28.9.2009,  10:01 Найти цитируемый пост)
Другой вопрос: "А какое вообще в данном случае имеет значение, как организована память структуры?". Допустим, то что тебе надо возможно. Какие выгоды ты собираешься из этого извлечь? Что такого можно сделать со структурой, когда она "содержит массив, а не ссылку"?

Более высокая скорость выделения памяти.


Потестил, и сделал на буферах фиксированного размера.
Если делать структуры с обычным ссылочным массивом, то торможение феерическое (при выделении массива из 1млн таких структур).

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)