Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > C/C++ программирование > Общие вопросы C/C++
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 03.09.2013, 22:04   #11
Igor95
Форумчанин
 
Регистрация: 03.01.2013
Сообщений: 388
По умолчанию

Цитата:
Сообщение от Vladiger Посмотреть сообщение
А если вообще, то даже не знаю что сказать. Ну вроде код как код.
Единственное о чём можно упомянуть, это сразу привыкать к хорошему тону програмиста, если конечно Вам это нужно.

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

Начните хотя бы с форматирования кода отступами, которые гораздо заметнее табуляциями, чем пробелами. Пока Ваш код слишком маленький и маленькие отступы не сильно сбивают Вас с толку, но когда Ваш код разрастется и превратится в тысячи строк, Вы потом сами запутаетесь в блоках вашей программы.

И ещё имена переменных, об этом где то статью читал (сейчас уже не помню ссылку). Вроде бы в них нет ничего криминального, Вы програмист, Вам и придумывать эти имена, какие хотите. Но правилом хорошего тона, будет считаться то, что имена этих переменных будут понятны другим програмистам, которые будут читать ваш код... Более того, в именах переменных, не плохо бы ссылаться и на их тип, по этому поводу тоже есть некие правила. То есть если переменная строка, то в вашем случае гораздо "вежлевее" было именовать переменную imya как strName, а переменные intiger можно было именовать как nAge, а не vozrast. Да, да, именно по Английски, а не транслитом. Если хотите програмировать, привыкайте к Английскому языку, хотя бы с переводчиком...

Почему Вам не пришло в голову именовать переменные по Русски и Русскими буквами, ведь это не запрещено, более того это возможно. Компилятор запросто проглатывает Кирилицу, так что вся Ваша программа может выглядеть например так:

Код:
#include <string>
#include <iostream>

using std::string;
using namespace std;

class Человек {
	public:
		Человек(string параметрИмени = "Безымянный", int параметрВозраста = 0, int параметрВес = 0, int параметрРост = 0, string параметрМестоРождения = "Марс") {
			Имя = параметрИмени;
			Возраст = параметрВозраста;
			Вес = параметрВес;
			Рост = параметрРост;
			МестоРождения = параметрМестоРождения;
		}

		string Имя;
		int Возраст;
		int Вес;
		int Рост;
		string МестоРождения;
		void Вывод();
};


void Человек::Вывод() {
	cout << "Имя: " << Имя << "\nВозраст: " << Возраст << "\nВес: " << Вес << "\nРост: " << Рост << "\nМесто рождения: " << МестоРождения << "\n";
}


int main() {
	setlocale(LC_ALL, "Rus");
	Человек Первый("Васёк", 20, 170, 120, "Китай");
	Первый.Вывод();
	system("pause");
	return 0;
}
Правда красиво?
При том прошу заметить, код прекрасно компилируется и работает.
И тем не менее - это сарказм. Не делайте так никогда...

Это конечно мелочи, на работу они не влияют. Я повторюсь: - Это просто признаки хорошего тона, а уж следовать этому хорошему тону или нет, дело Ваше...
Это кто же будет именовать переменные на русском? Это уже перебор, есть определенные конвенции, принятые программистами... нужно же соблюдать
Igor95 вне форума Ответить с цитированием
Старый 03.09.2013, 22:08   #12
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Цитата:
Сообщение от Igor95 Посмотреть сообщение
Конструкторы в C++ служат для созддания объекта, т.е выделения памяти для хранения его данных-членов.
Неверно. Конструкторы не занимаются выделением памяти. Только её инициализацией.

К моменту запуска списка инициализации конструктора, вся необходимая память уже выделена (this объекта реально существует).
_Bers вне форума Ответить с цитированием
Старый 03.09.2013, 22:53   #13
Igor95
Форумчанин
 
Регистрация: 03.01.2013
Сообщений: 388
По умолчанию

Цитата:
Сообщение от _Bers Посмотреть сообщение
Неверно. Конструкторы не занимаются выделением памяти. Только её инициализацией.

К моменту запуска списка инициализации конструктора, вся необходимая память уже выделена (this объекта реально существует).
Да, точно, ошибся. Ведь, например, при динамическом создании объекта сначала выделяется память, а только, затем, вызывается конструктор.
Спасибо за указание на ошибку
Igor95 вне форума Ответить с цитированием
Старый 03.09.2013, 23:16   #14
Vladiger
Пользователь
 
Регистрация: 31.08.2013
Сообщений: 93
По умолчанию

Вот ещё обратил внимание:
Цитата:
/* данные класса специально открытые (public) что бы не писать
функции get и set, что бы не тратить просто так время */
Ну все таки не просто так же свойства класса стараются делать приватными и не делая их публичными без видимой на то причины. Причины видимо есть.

А по поводу "тратить время", не знаю пригодится ли Вам или нет, но не в качестве совета, а скорее просто поделюсь информацией к размышлению...

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

Код:
string GetName() {
	return strName;
}

string SetName(string Name) {
	strName = Name;
}
И так для каждой переменной. Получится действительно слижком много кода и времени, но все это можно существенно сократить используя макросы. Если взять за правило, все переменные в классе именовать начиная с префикса (например m_) то для каждого из свойств можно описать оба метода Get и Set одним лишь макросом (одной строчкой), при том короткой.

Приведу пример кода Вашего класса, где все свойства приватны и к каждому из них уже есть методы Get и Set.

Код:
#include <string>
#include <iostream>

#define SET_ACCESSOR(x, y) inline void Set##y(x t) { m_##y = t; };
#define GET_ACCESSOR(x, y) inline x Get##y() { return m_##y; };
#define GET_SET_ACCESSOR(x, y) SET_ACCESSOR(x, y) GET_ACCESSOR(x, y)

using namespace std;

class People {
	public:
		People(string strName = "Безымянный", int nAge = 0, int nWeight = 0, int nHeight = 0, string strBirthplace = "Марс") {
			m_Name = strName;
			m_Age = nAge;
			m_Weight = nWeight;
			m_Height = nHeight;
			m_Birthplace = strBirthplace;
		}

		void doOutput() {
			cout << "Имя: " << m_Name << endl;
			cout << "Возраст: " << m_Age << endl;
			cout << "Вес: " << m_Weight << endl;
			cout << "Рост:" << m_Height << endl;
			cout << "Место рождения:" << m_Birthplace << endl;
		}

		// Объявление методов Get и Set для приватных свойств класса
		GET_SET_ACCESSOR(string, Name);
		GET_SET_ACCESSOR(int, Age);
		GET_SET_ACCESSOR(int, Weight);
		GET_SET_ACCESSOR(int, Height);
		GET_SET_ACCESSOR(string, Birthplace);

	private:
		string m_Name;
		int m_Age;
		int m_Weight;
		int m_Height;
		string m_Birthplace;
};


int main() {
	setlocale(LC_ALL, "Rus");
	People First("Васёк", 20, 170, 120, "Китай");

	First.doOutput();
	cout << endl;

	// Изменяем приватные свойства класса методом Set
	First.SetName("Сергей");
	First.SetAge(20);
	First.SetWeight(70);
	First.SetHeight(175);
	First.SetBirthplace("Бейрут");

	// Читаем приватные свойства класса методом Get
	cout << "Имя: " << First.GetName() << endl;
	cout << "Возраст: " << First.GetAge() << endl;
	cout << "Вес: " << First.GetWeight() << endl;
	cout << "Рост:" << First.GetHeight() << endl;
	cout << "Место рождения:" << First.GetBirthplace() << endl;
	system("pause");
	return 0;
}
Вся прелесть в макросах GET_ACCESSOR(тип, имя переменной), SET_ACCESSOR(тип, имя переменной) и GET_SET_ACCESSOR(тип, имя переменной). Добавляя в класс новую приватную переменную с префиксом m_ (например bool m_Smoking), в секции public: просто дописываете макрос GET_SET_ACCESSOR(bool, Smoking); где имя переменной пишем уже без префикса...
При том макрос GET_SET_ACCESSOR установит оба метода и Get и Set, но можно назначать каждому свойству ограниченный доступ, например только чтение GET_ACCESSOR(bool, Smoking), только запись SET_ACCESSOR(bool, Smoking)...

Последний раз редактировалось Vladiger; 03.09.2013 в 23:18.
Vladiger вне форума Ответить с цитированием
Старый 03.09.2013, 23:29   #15
Igor95
Форумчанин
 
Регистрация: 03.01.2013
Сообщений: 388
По умолчанию

А зачем так извращаться? ведь можно просто объявить и определить методы для работы с данными объекта. Зачем здесь макросы? Затрата времени на процесс компиляции, отрабатает препроцессор -Ю заменит макросы их определениями... зачем? А метод inline и так объявить можно, без макросов.
Igor95 вне форума Ответить с цитированием
Старый 03.09.2013, 23:47   #16
Vladiger
Пользователь
 
Регистрация: 31.08.2013
Сообщений: 93
По умолчанию

Ключевым моментом является:
Цитата:
что бы не тратить просто так время
На этом как бы и сосредоточил внимание. Макросы действительно не обязательны вовсе, но это экономит кучу времени при написании, ведь объявив эти макросы в заголовке основного файла решения (каком нибудь Main.h) их можно использовать в любом другом классе...

Ну лень человеку писать на каждую переменную:
Код:
inline string GetName() {
	return strName;
}

inline void SetName(string Name) {
	strName = Name;
}
и.т.д и.т.п... ведь гораздо короче запись GET_SET_ACCESSOR(string, Name); при том в одну строку сразу оба метода и Get и Set...

Тут нет выгоды в функционале, тут выгода в элементарном сокращении кода, т.е. чисто человеческий фактор.

Можно конечно и руками все это описать, без макросов, но вот по секрету скажу, мне тоже лень, я постоянно такими штуками пользуюсь!

А время на компиляцию не думаю что изменится. Компилятору не все ли равно что компилировать, объявленные методы Get и Set вручную, либо объявить их макросом... Все то же самое. Я ведь не говорю о том что эти методы нужно объявлять на каждую переменную, только на те к которым нужен доступ.
Vladiger вне форума Ответить с цитированием
Старый 03.09.2013, 23:51   #17
Igor95
Форумчанин
 
Регистрация: 03.01.2013
Сообщений: 388
По умолчанию

Цитата:
Сообщение от Vladiger Посмотреть сообщение
Ключевым моментом является:


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

Ну лень человеку писать на каждую переменную:
Код:
inline string GetName() {
	return strName;
}

inline void SetName(string Name) {
	strName = Name;
}
и.т.д и.т.п... ведь гораздо короче запись GET_SET_ACCESSOR(string, Name); при том в одну строку сразу оба метода и Get и Set...

Тут нет выгоды в функционале, тут выгода в элементарном сокращении кода, т.е. чисто человеческий фактор.

Можно конечно и руками все это описать, без макросов, но вот по секрету скажу, мне тоже лень, я постоянно такими штуками пользуюсь!

А время на компиляцию не думаю что изменится. Компилятору не все ли равно что компилировать, объявленные методы Get и Set вручную, либо объявить их макросом... Все то же самое. Я ведь не говорю о том что эти методы нужно объявлять на каждую переменную, только на те к которым нужен доступ.
Да, вот только не будет осуществлятся проверка типов данных.
Igor95 вне форума Ответить с цитированием
Старый 04.09.2013, 00:15   #18
pproger
C++ hater
СтарожилДжуниор
 
Аватар для pproger
 
Регистрация: 19.07.2009
Сообщений: 3,333
По умолчанию

2Vladiger
отвратительно. ты понимаешь, что люди это придумавшие (COM, DX, MFC) писали в те времена на "C с классами"? сейчас такой код только вводит в заблуждение. эти люди (а соответственно и ты, ибо скопипастил) даже геттер константным не сделали. захочешь в один из геттеров/сеттеров добавить отладочный вывод/контроль данных, и он уже будет выбиваться из общей массы. добавлять таким образом "новые конструкции" в язык - практически всегда плохо. лень много писать? освой уже свой инструмент (ide/редактор), и напиши сниппет.
I invented the term Object-Oriented, and I can tell you I did not have C++ in mind. (c)Alan Kay

My other car is cdr.

Q: Whats the object-oriented way to become wealthy?
A: Inheritance
pproger вне форума Ответить с цитированием
Старый 04.09.2013, 00:30   #19
Vladiger
Пользователь
 
Регистрация: 31.08.2013
Сообщений: 93
По умолчанию

Цитата:
ибо скопипастил
Разумеется, а разве я где то претендовал на Авторство?
Я даже более скажу, скажу откуда скопипастил:
DirectX Software Development Kit в состав SDK входит графический интерфейс DXUT, открытость кода и никаких запретов на макросы я не нашел.

А что отвратительно то? То что пишу программы на языке высокого уровня используя пускай не все, но все известные мне средства?
Ну хорошо, я учту. Переходим на Dos и Ассемблер, надеюсь он никого не введет в заблуждение.
Vladiger вне форума Ответить с цитированием
Старый 04.09.2013, 00:33   #20
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Vladiger,

1. Без видимой причины не нужно делать данные приватными.

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

3. Методы, определенные в декларации класса по стандарту уже являются inline. Не нужно дополнительно указывать это компилятору.
К тому же, современные компиляторы стали достаточно умны. Умеют инлайнтить даже те методы, которые разбросаны по разным единицам трансляции.

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

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

Актуальность сохраняют ключевые слова, например: __forceinline
Это расширение от компилятора майкрософт.
Приказ компилятору инлайнтить функцию "крутись как хочешь, но сделай".
Неаккуратное использование может просадить производительность.
_Bers вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Обновление поля формы после создания новой записи создания romanln2012 Microsoft Office Access 2 09.08.2012 14:12
Подскажыте програму для создания gif-анимаций, которые после создания не теряют четкости pufystyj Софт 1 24.02.2011 01:50
Автоматическое преобразование на основе первого аргумента конструктора в вызов самого конструктора jennya Visual C++ 8 03.10.2010 19:03
Создание конструктора Superlotles Общие вопросы C/C++ 5 23.05.2010 01:38
Правила разделов/главные правила Alex Cones О форуме и сайтах клуба 1 30.09.2009 17:49