Переменные могут быть полями класса, объявляться в функциях или даже внутри циклов (например: for (int i=0; i

Область видимости, или контекст переменной — это часть кода, в пределах которого доступна данная переменная. В общем случае такая область определяется описанными ниже правилами:
1. Поле, также известное как переменная-член класса, находится в области видимости до тех пор, пока в этой области находится содержащий поле класс.
2. Локальная переменная находится в области видимости до тех пор, пока закрывающая фигурная скобка не укажет конец блока операторов или метода, в котором она объявлена.
3. Локальная переменная, объявленная в операторах цикла for, while или подобных им, видима в пределах тела цикла.

Конфликты областей видимости локальных переменных.
Использование в больших программах одних и тех же имен переменных в разных частях программы является обычной практикой. Это нормально до тех пор, пока области видимости этих переменных не перекрываются и находятся в совершенно разных частях программы, таким образом, исключая любую неоднозначность.

Однако следует иметь в виду, что локальные переменные с одним и тем же именем не могут быть объявлены дважды в одном и том же контексте, поэтому вы не сможете поступить так, как показано ниже:
int х = 20;
// какой-то код
int х = 30;

Рассмотрим следующий пример кода с локальной переменной k (оператор цикла for изучается дальше):

Важно отметить, что переменная k объявляется в этом коде два раза в пределах одного и того же метода Main(). Это можно делать, поскольку переменные k объявляются в двух отдельных циклах, поэтому каждая из них локальна в пределах собственного цикла.
Рассмотрим другой пример:

Если вы попытаетесь скомпилировать это, то получите следующее сообщение об ошибке:
Ошибка: Невозможно объявить локальную переменную с именем «k» в этой области видимости, т.к. она придаст другое значение «k», которая уже используется в области видимости «родительский или текущий» для обозначения чего-то другого.
Дело в том, что переменная k, которая определена перед началом цикла for, внутри цикла все еще находится в области видимости и не может из нее выйти до завершения метода Main().
Хотя вторая переменная k (недопустимая) объявлена в контексте цикла, этот контекст вложен в контекст метода Main(). Компилятор не может различить эти две переменных, поэтому не допустит объявления второй из них.

Конфликты областей видимости полей и локальных переменных. В некоторых случаях два идентификатора с одинаковыми именами (хотя и не совпадающими полностью уточненными именами) и одинаковой областью видимости можно различить, и тогда компилятор допускает объявление второй переменной. Причина в том, что C# делает принципиальное различие между переменными, объявленными на уровне типа (в примере — полями класса) и переменными, объявленными в методах (локальными переменными).

Рассмотрим третий пример:

Этот код компилируется, несмотря на то, что здесь в контексте метода Main() присутствуют две переменных с именем k: переменная k, определенная на уровне класса и существующая до тех пор, пока не будет уничтожен класс (когда завершится метод Main(), а вместе с ним и программа), и переменная k, определенная внутри Main().

В данном случае новая переменная с именем k, объявленная в методе Main(), игнорирует переменную уровня класса с тем же именем. Поэтому когда вы запустите этот код, на дисплее будет отображено число 30.
В языке C# локальные переменные широко используются именно из-за аппарата разграничения области видимости. Не экономьте без необходимости на локальных переменных, если они не занимают большой объем памяти.

Следующее интуитивно понятие языка программирования — Литералы.

Необходимо воспользоваться в классе C полями класса A. Как это возможно сделать? Вне классов создавать переменные нельзя, дальше уже namespace

1 ответ 1

Автор, если тебе действительно нужны "глобальные переменные", то в .NET это static-поля и свойства.

Но если тебе нужно просто разделить общий ресурс между несколькими компонентами, то ты либо передаёшь один в конструктор или метод другого, делая поля/свойства публичными, либо выносишь их в отдельный класс-контекст, который спускаешь в конструктор/метод каждого класса, который их использует. Основы ООП.

Я хочу, чтобы некоторые переменные были глобальными по всему проекту и доступными в любой форме. Как я могу это сделать?

8 ответов

да, вы можете использовать статический класс. вот так:

и через любой, где вы можете написать:

или вы можете поместить свои глобалы в app.config

Обозреватель > Проект > Свойства > Параметры.Настройки. Нажмите на этот файл и добавьте определение параметров из среды IDE.

консенсус здесь заключается в том, чтобы поместить глобальные переменные в статический класс как статические члены. Когда вы создаете новое приложение Windows Forms, оно обычно поставляется с классом программы (Program.cs), который является статическим классом и служит основной точкой входа приложения. Он живет на всю жизнь приложения, поэтому я думаю, что лучше поместить глобальные переменные там, а не создавать новый.

и используйте его как таковой:

Если вы используете Visual C# все, что вам нужно сделать, это добавить класс в программу.cs наследует форму и изменяет весь унаследованный класс из формы в ваш класс в каждой форме*.цезий.

конечно, может быть способ расширение формы класса без ее изменения. Если это так, все, что вам нужно сделать, это продлить его! Поскольку все формы наследуют его по умолчанию, все объявленные в нем ценности автоматически станут глобальными! Хороший удачи.

они уже ответили, как использовать глобальную переменную.

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

явный перевод текста на испанском языке:

проблема с глобальными переменными заключается в том, что они создают скрытых зависимостей. Когда дело доходит до больших приложений, вы вы сами не знаете / помните / вы ясно представляете себе объекты, которые у вас есть, и их отношения.

таким образом, вы не можете иметь четкое представление о том, сколько объектов использует ваша глобальная переменная. А если вы хотите изменить что-то из глобальной переменной, например, значение каждого из ее возможных значений или ее тип? На сколько классов или единиц компиляции это повлияет? Если сумма небольшая, возможно, стоит внести изменения. Если удар будет большим, то он может быть стоит поискать другое решение.

но каковы последствия? Поскольку глобальная переменная может использоваться в любом месте кода, ее может быть очень сложно измерить.

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

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

еще одна проблема-порядок уничтожения. Переменные всегда уничтожаются в обратном порядке их создания, будь то локальные или глобальные / статические переменные (исключение составляют примитивные типы, int , enum s и т. д., который никогда не уничтожаются, если они являются глобальными / статическими, пока они не закончат программу).

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

если все ваши глобальные / статические переменные в одном модуле компиляции (то есть, у вас есть только .cpp ), то порядок построения такой же, как и у записи (то есть переменные, определенные ранее, строятся до.)

но если у вас больше одного .cpp каждый со своими глобальными / статическими переменными, глобальный порядок построения является неопределенным. Конечно, порядок в каждой единице компиляции (каждый .cpp ) в частности, соблюдается: если глобальная переменная A определен до B , A будет построен до B , но возможно, что между A и B переменные другие .cpp инициализируются. Например, если у вас есть три единицы с следующие глобальные / статические переменные:

в исполняемом файле он может быть создан в этом порядке (или в любом другом порядке, если относительный порядок соблюдается в каждом .cpp ):

почему это важно? Потому что если существуют отношения между различными статическими глобальными объектами, например, что некоторые используют другие в своих деструкторах, возможно, в деструкторе глобального переменная, вы используете другой глобальный объект из другого блока компиляции, который оказывается уже уничтоженным (были построены позже).

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

представьте, что у вас есть платежная система, и вы хотите протестировать ее, чтобы увидеть, как она работает, так как вам нужно внести изменения, а код от другого человека (или вашего, но от нескольких лет назад). Вы открываете новый main , и вы вызываете соответствующую функцию вашего глобального объекта, который предоставляет услугу банковского платежа с картой, и оказывается, что вы вводите свои данные, и они взимают с вас плату. Как, в простом тесте, я используется производственная версия? Как я могу сделать простой платежный тест?

после запроса других сотрудников выясняется, что вы должны "отметить true", глобальный bool, который указывает, находимся ли мы в тестовом режиме или нет, прежде чем начать процесс сбора. Ваш объект, предоставляющий платежную услугу, зависит от другого объекта, предоставляющего способ оплаты, и эта зависимость возникает невидимым для программиста образом.

другими словами, глобальные переменные (или singletones), сделать невозможным переход в "тестовый режим", поскольку глобальные переменные не могут быть заменены экземплярами "тестирования" (если вы не измените код, в котором этот код создан или определен). глобальная переменная, но мы предполагаем, что тесты выполняются без изменения материнского кода).

это решается с помощью так называемой * инъекции зависимостей*, которая заключается в передаче в качестве параметра всех зависимостей, которые нужны объекту в его конструкторе или в соответствующем методе. Таким образом, программист * * видит **, что с ним должно произойти, так как он должен писать его в коде, что дает разработчикам много времени.

если слишком много глобальных объектов и слишком много параметров в функциях, которым они нужны, вы всегда можете сгруппировать свои "глобальные объекты" в класс style * factory *, который строит и возвращает экземпляр "глобального объекта" (смоделированный), который вы хотите, передавая фабрику в качестве параметра к объектам, которые нуждаются в глобальном объекте как зависимости.

при переходе в тестовый режим всегда можно создать фабрику тестирования (которая возвращает разные версии одних и тех же объектов) и передать ее в качестве параметра без необходимости изменять целевой класс.

не обязательно, может быть хорошее использование для глобальных переменных. Например, постоянные значения (значение PI). Быть постоянн значением, никакой риск не знать свое значение в заданной точке программы по любому типу модификации из другого модуля. Кроме того, постоянные значения имеют тенденцию быть примитивными и вряд ли изменят свое определение.

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

другой может быть неинтрузивными "глобальными" службами, такими как класс ведения журнала (сохранение того, что происходит в файле, который обычно необязательный и настраиваемый в программе, и поэтому не влияет на ядерное поведение приложения), или std :: cout , std :: cin или std :: cerr , которые также являются глобальными объектами.

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