Форум программистов, компьютерный форум, киберфорум
C# для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.83/18: Рейтинг темы: голосов - 18, средняя оценка - 4.83
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76

Ссылочные типы данных и интерфейсы

24.02.2019, 17:34. Показов 3629. Ответов 12
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Есть некоторый проект, в котором реализованы тесты:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
[TestFixture]
    public class GhostsTest
    {
        [Test]
        public void GhostVectorBreaksHashSet()
        {
            AssertThatDoMagicBreaksHashSet<Vector, GhostsTask>();
        }
 
        private void AssertThatDoMagicBreaksHashSet<TItem, TGhostsTask>() where TGhostsTask : IMagic, IFactory<TItem>, new()
        {
            TGhostsTask task = new TGhostsTask();
            var ghostItem = task.Create();
 
                        // далее код который не имеет значения.....
        }
Что тут происходит, я вызываю метод AssertThatDoMagicBreaksHashSet с generic параметрами, класс Vector и класс GhostsTask, где GhostsTask должен реализовывать интерфейсы Magic, IFactory<TItem>. Здесь же создаю экземпляр класса GhostsTask, вот код этого класса:

C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
public class GhostsTask :  IFactory<Vector>,  IMagic
    {
        public Vector item1;
 
        public void DoMagic()
        {
            item1.Add(new Vector(2, 2));
        }
 
        Vector IFactory<Vector>.Create()
        {
            item1 = new Vector(1, 1);
            return item1;
        }
    }
Этот класс реализует, как и обещал, интерфейс IMagic и IFactory<Vector>.
Далее продолжаем в тестах, переменой ghostItem присваиваю значение task.Create(); Я ожидаю что переменная item1 в классе GhostsTask и переменная ghostItem(из тестов) будут ссылкой на один и тот же объект типа Vector. Но почему то это не так, изменяя переменную item1 в методе DoMagic() я хочу что бы менялась переменная ghostItem в тестах. Но это так не работает, понятия не имею почему так происходит!

Доп. код: интерфейсов и метода Vector.Add():

1) Интерфейсы
C#
1
2
3
4
5
6
7
8
    public interface IMagic
    {
        void DoMagic();
    }
    public interface IFactory<out T>
    {
        T Create();
    }
2) Метод Vecor.Add()
C#
1
2
3
4
5
6
        public Vector Add(Vector other)
        {
            X += other.X;
            Y += other.Y;
            return this;
        }
0
Лучшие ответы (1)
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
24.02.2019, 17:34
Ответы с готовыми решениями:

Ссылочные типы данных
Эксперементирую с клонированием экземпляров класса. В данном случаем клонирую экземпляр класса а в переменную b. При клонировании...

Значимые и ссылочные типы данных
Тип int - значимый тип данных, соответственно и переменные этого типа хранятся в стеке. Меня интересует, каким типом (значимым или...

Типы значения и ссылочные типы
Здравствуйте. Мог бы кто-нибудь простыми словами объяснить что такое типы значения и ссылочные типы применительно к структурам? ...

12
 Аватар для samana
2639 / 1567 / 853
Регистрация: 23.02.2019
Сообщений: 3,876
24.02.2019, 17:37
А Vector случайно не структура? Если да, то вы наверно помните, что структуры передаются по значению, а не по ссылке.
0
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76
24.02.2019, 17:40  [ТС]
0
 Аватар для samana
2639 / 1567 / 853
Регистрация: 23.02.2019
Сообщений: 3,876
24.02.2019, 18:37
Создал подобную структуру как у вас, но воспроизвести проблему не получилось, всё меняется так, как и ожидалось.
Попробуйте пройтись дебагером и определить место, где происходит непредвиденный сбой.
0
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76
24.02.2019, 20:28  [ТС]
Ссылка на проект https://drive.google.com/file/... sp=sharing

Добавлено через 1 минуту
Сбоя нет, он просто меняет значение одной из переменных. Другую переменную не трогает, как будто так и нужно.

Добавлено через 1 минуту
В проекте пока интересны три файла, Vector, GhostsTask и GhostsTest

Добавлено через 22 минуты
Не пробовали еще? Такой же результат как у меня?

Добавлено через 1 час 14 минут
Help! Please, Help!
0
 Аватар для samana
2639 / 1567 / 853
Регистрация: 23.02.2019
Сообщений: 3,876
24.02.2019, 21:57
Да, я попробовал открыть ваш проект, там почему-то не совсем корректно открылось, но не суть, я убрал то, что не касалось вопроса.
Для проверки я сделал некоторые изменения. Временно добавил в класс Vector метод, чтобы хоть как-то увидеть значения его свойств, а то ведь совсем нет доступа к ним ниоткуда

C#
1
2
3
4
public override string ToString()
{
    return $"X={X} Y={Y}";
}
А в классе Program напрямую создал объект GhostsTest и вызвал нужный вам метод AssertThatDoMagicBreaksHashSet

C#
1
2
3
4
5
6
7
8
9
10
11
namespace ghost
{
    class Program
    {
        static void Main(string[] args)
        {
            GhostsTest ghostsTest = new GhostsTest();
            ghostsTest.AssertThatDoMagicBreaksHashSet<Vector, GhostsTask>();
        }
    }
}
А вот в самом методе AssertThatDoMagicBreaksHashSet получал доступ к векторам через каст и как видите в коде ниже, переменная ghostItem и item1 ссылаются на один и тот же вектор. В коде я изменил item1 и всё так же отразилось на ghostItem. Поэтому я даже не знаю, почему у вас не работает так как надо..

C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
public void AssertThatDoMagicBreaksHashSet<TItem, TGhostsTask>() where TGhostsTask : IMagic, IFactory<TItem>, new()
{
    TGhostsTask task = new TGhostsTask();
    var ghostItem = task.Create();
 
 
    System.Console.WriteLine(ghostItem as Vector);    //X=1 Y=1
    System.Console.WriteLine((task as GhostsTask).item1); //X=1 Y=1
 
 
    (task as GhostsTask).item1.Add(new Vector(5, 5));
 
    System.Console.WriteLine(ghostItem as Vector);    //X=6 Y=6
    System.Console.WriteLine((task as GhostsTask).item1); //X=6 Y=6
 
}
1
Эксперт .NET
6691 / 4102 / 1607
Регистрация: 09.05.2015
Сообщений: 9,574
24.02.2019, 21:58
Цитата Сообщение от Mark0111 Посмотреть сообщение
Я ожидаю что переменная item1 в классе GhostsTask и переменная ghostItem(из тестов) будут ссылкой на один и тот же объект типа Vector. Но почему то это не так
Потому что вы 2 раза вызываете Create, тем самым изменяя item1.
0
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76
24.02.2019, 22:29  [ТС]
Цитата Сообщение от Someone007 Посмотреть сообщение
Потому что вы 2 раза вызываете Create, тем самым изменяя item1.
Почему 2 раза. Только 1.

Вот в обсуждении к этому заданию нашел:


"все правильно делаешь,
только сохранять надо в сущность другого типа,
поэкспериментируй."
"В сущность такого типа, которая содержит множество экземпляров одного типа.
Думай, экспериментируй."

………..
0
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76
24.02.2019, 22:50  [ТС]
ссылка на задание https://ulearn.me/Course/Basic... f38fba7acc
0
Эксперт .NET
6691 / 4102 / 1607
Регистрация: 09.05.2015
Сообщений: 9,574
24.02.2019, 22:53
Лучший ответ Сообщение было отмечено Mark0111 как решение

Решение

Цитата Сообщение от Mark0111 Посмотреть сообщение
Почему 2 раза. Только 1.
А это что тогда?
Миниатюры
Ссылочные типы данных и интерфейсы  
1
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76
24.02.2019, 23:09  [ТС]
Точно! Спасибо большое! Тогда можно вместо Vector item1 сделать массив Vector[] item1, и менять первый.
0
Эксперт .NETАвтор FAQ
 Аватар для Storm23
10427 / 5157 / 1825
Регистрация: 11.01.2015
Сообщений: 6,226
Записей в блоге: 34
24.02.2019, 23:39
Цитата Сообщение от Mark0111 Посмотреть сообщение
Но почему то это не так, изменяя переменную item1 в методе DoMagic() я хочу что бы менялась переменная ghostItem в тестах. Но это так не работает, понятия не имею почему так происходит!


PS Блин, форум тормозит, не обновилась страница, не увидел обсуждения
1
6 / 5 / 1
Регистрация: 24.10.2018
Сообщений: 76
24.02.2019, 23:44  [ТС]
Спасибо! Судя по комментам на странице с заданием, я не один попался в эту ловушку.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
24.02.2019, 23:44
Помогаю со студенческими работами здесь

Ссылочные и значимые типы, разобрать пример
Во всех книга расписываются следующий образом. Ссылочный тип - ссылка на объект в куче, значимый - объект в стеке, работа идет с его...

Вопрос про ссылочные типы и object
Пишу на C#. Прочитал в книге, про то как перейти от типа, характеризуемого значением, к ссылочному типу. Написано что для этого можно...

Ссылочные типы и полиморфизм, приведение пользовательских типов
Здравствуйте! Не могу въехать в одну концепцию, а именно - приведение пользовательских типов. Если приведение встроенных типов не...

Значимые и ссылочные типы. Куча и стек. И всем таким темам посвящается
А вот у меня на все бывшие и будущие вопросы про стек и кучу возник такой вопрос class Program { int j=3; ...

Где найти подробную информацию про ссылочные и значимые типы, стек и управляемую кучу
Где найти подробную инфу про ссылочные и значимые типы, стек и управляемую кучу, что откуда летит и куда и т.д. подробно с...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
13
Ответ Создать тему
Новые блоги и статьи
SDL3 для Web (WebAssembly): Основы отладки веб-приложений на SDL3 по USB и Wi-Fi, запущенных в браузере мобильных устройств
8Observer8 07.02.2026
Содержание блога Браузер Chrome имеет средства для отладки мобильных веб-приложений по USB. В этой пошаговой инструкции ограничимся работой с консолью. Вывод в консоль - это часть процесса. . .
SDL3 для Web (WebAssembly): Обработчик клика мыши в браузере ПК и касания экрана в браузере на мобильном устройстве
8Observer8 02.02.2026
Содержание блога Для начала пошагово создадим рабочий пример для подготовки к экспериментам в браузере ПК и в браузере мобильного устройства. Потом напишем обработчик клика мыши и обработчик. . .
Философия технологии
iceja 01.02.2026
На мой взгляд у человека в технических проектах остается роль генерального директора. Все остальное нейронки делают уже лучше человека. Они не могут нести предпринимательские риски, не могут. . .
SDL3 для Web (WebAssembly): Вывод текста со шрифтом TTF с помощью SDL3_ttf
8Observer8 01.02.2026
Содержание блога В этой пошаговой инструкции создадим с нуля веб-приложение, которое выводит текст в окне браузера. Запустим на Android на локальном сервере. Загрузим Release на бесплатный. . .
SDL3 для Web (WebAssembly): Сборка C/C++ проекта из консоли
8Observer8 30.01.2026
Содержание блога Если вы откроете примеры для начинающих на официальном репозитории SDL3 в папке: examples, то вы увидите, что все примеры используют следующие четыре обязательные функции, а. . .
SDL3 для Web (WebAssembly): Установка Emscripten SDK (emsdk) и CMake для сборки C и C++ приложений в Wasm
8Observer8 30.01.2026
Содержание блога Для того чтобы скачать Emscripten SDK (emsdk) необходимо сначало скачать и уставить Git: Install for Windows. Следуйте стандартной процедуре установки Git через установщик. . . .
SDL3 для Android: Подключение Box2D v3, физика и отрисовка коллайдеров
8Observer8 29.01.2026
Содержание блога Box2D - это библиотека для 2D физики для анимаций и игр. С её помощью можно определять были ли коллизии между конкретными объектами. Версия v3 была полностью переписана на Си, в. . .
Инструменты COM: Сохранение данный из VARIANT в файл и загрузка из файла в VARIANT
bedvit 28.01.2026
Сохранение базовых типов COM и массивов (одномерных или двухмерных) любой вложенности (деревья) в файл, с возможностью выбора алгоритмов сжатия и шифрования. Часть библиотеки BedvitCOM Использованы. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru