Вы видите копию треда, сохраненную 4 августа 2015 года.
Скачать тред: только с превью, с превью и прикрепленными файлами.
Второй вариант может долго скачиваться. Файлы будут только в живых или недавно утонувших тредах. Подробнее
Если вам полезен архив М.Двача, пожертвуйте на оплату сервера.
Я увожу через шаблонов стон,
Я увожу к олдфажным наставлениям.
Был Симулой мой Зодчий вдохновлён:
Я высшей силой, полнотой всезнанья
И чистым байтоебством сотворён.
Древней меня лишь вечные созданья,
И с вечностью пребуду наравне.
Входящие, оставьте упованья.
Литература:
Для нюфань:
Три классических учебника для начинающих. Все примерно одинаковой годноты, читать имеет смысл только какой-нибудь один, который больше приглянется.
Герберт Шилдт - C++. Базовый курс - http://padabum.com/x.php?id=15127
Роберт Лафоре - Объектно-ориентированное программирование в C++ - http://padabum.net/x.php?id=16885
Стивен Прата - Язык программирования C++ - http://bukin.su/share/%D0%9A%D0%BD%D0%B8%D0%B3%D0%B8/cpp/Prata_C++.pdf
Учимся не писать говнокод:
Книги про основные подводные камни для тех, кто осилил предыдущий пункт. Следует пролистать все.
Скотт Мейерс - Эффективное использование C++ - http://www.e-reading.club/book.php?book=1002058
Скотт Мейерс - Наиболее эффективное использование C++ - http://www.proklondike.com/var/file/C/Scott_Meyers_-_More_Effective_CPP(RUS).rar
Герб Саттер и Андрей Александреску - Стандарты программирования на языке C++ - http://coollib.com/b/176648
Тонкости языка (для гурманов):
Ад и хардкор.
Бьерн Страуструп - Язык программирования C++ - http://www.proklondike.com/var/file/straustrup-yazyk-c-speciazdanie.zip
Андрей Александреску - Современное проектирование на C++ - http://www.proklondike.com/var/file/C/Andrei_Alexandrescu_-_Sovremennoe_Proectirovanier_CPP.rar
Герб Саттер - Решение сложных задач на C++ - http://www.studfiles.ru/dir/cat32/subj1104/file8061.html
Стандарт языка (на ангельском) - http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf
Отдельные аспекты:
Читать по необходимости.
Энтони Уильямс - Параллельное программирование на C++ в действии - http://www.proklondike.com/var/file/Paralelnie_programirovanie.zip
Николаи Джоссатис - C++. Стандартная библиотека - http://www.proklondike.com/var/file/C/Nicolai_Josuttis_-_STL(RUS).rar
Ссылки:
Годный блог, в котором все просто и понятно тян не нужны кококок борщ - http://alenacpp.blogspot.ru/
Краткие описания библиотечных функций и контейнеров - http://ru.cppreference.com/w/
Памятка:
Вопросу по синтаксису идут на хуй.
Лабы идут на хуй.
"Как мне сделать Х на чистых крестах без библиотек" идут на хуй.
Все идут на хуй.
Хейтер сосет члены на пару со своей мамашей.
Тег [code] работает через жабаскрипт-костыль: https://github.com/ololoepepe/MakabaCode
Предыдущий: >>489539
Ты программист, в тексте программерские термины, которые ты либо знаешь, либо легко вычленяешь глазами (потому что слышал) и резко гуглишь. Нет никаких проблем с терминами при чтении английского. Более того, проблема в терминах у меня исключительно и только в русскоязычных текстах. Русские тексты с переведённой терминологией меня скорее отвлекают, чем учат. Я просто не могу читать что-то по математике или программированию, если оно написано в рамках русской традиции наименования. Переведенные термины, как правило, по облику слов часто совершенно отличаются от того, что ты знаешь или хотя бы слышал. Легче, когда это простые кальки или транскрипции.
Добротность по-английски - Q. Если ты с этим ни разу не встречался, то ты в принципе не в теме этой области знаний.
> Переведенные термины, как правило, по облику слов часто совершенно отличаются от того, что ты знаешь или хотя бы слышал. Легче, когда это простые кальки или транскрипции.
Хуй знает что ты там читаешь.
Большинство современных текстов зачастую полны англицизмов, которые давно понятны.
На русском ничего не читаю практически. Ну открыл линк первый из шапки - именно то, о чем я говорил. Открыл незнакомый раздел, куча переводных терминов, которые я даже могу не узнать, когда начну читать английский референс - подумаю, что учу что-то другое. Наоборот тоже справедливо - читаешь такой, и понимаешь, что речь-то идёт о том, что ты уже знал, просто слова странные какие-то.
Нет. Это сокращение от quality, но так никто не говорит. https://en.wikipedia.org/wiki/Q_factor
Principles and Practice Using C++
Бьярне написал. PDF полный есть у кого? В гуголе стастраничные обрезки.
Почему-то не подумал о трекерах. На рутрекере второе издание только на русском, но зато с сорсами. На кикэссе же есть английская книга без сорцев. Скрафчу из этого одно целое.
У goto есть аналоги, у break/continue - нет.
Структурным программированием наложено табу и на break, и на continue, и на множественные return и на большие вложенности и на небо с Аллахом.
Но так как уже 2015 и те проблемы с которыми боролся дiйкстра более не актуальны, то можно иногда и юзать, когда действительно нельзя адекватно избежать. Но лучше конечно подумать.
Хоть твой вопрос относится к pure С, отвчеу. goto использовать можно, если понимаешь что делаешь. break\continue мощнейшие операторы, использую вобще везде. А вот for как раз считаю злом, использую только в виде for(;;) - так норм.
Sooqa, я 500 сообщений ждал нового треда, посчитав зашкваром участвовать в предыдущем из-за ОП-пика. И вот опять, снова эта умелица с её void main() { exit(0); }
Убери это говно отсюда, блядь! Сейчас будешь это вылизывать, блядь!
%Она ОП этого треда, кто еще будет кидать ссылку на это говно%
Сегодня остаёмся без постов какого-то рандомного говнометателя?
Ты написал какой-то сокральный, код увидев который, я должен пасть ниц?
%Ну, а чем ты недоволен-то?%
В PERL МОЖНО ПОМЕТИТЬ МЕТКОЙ БЛОК ИЛИ ЦИКЛ И ДЕЛАТЬ BREAK CONTINUE С ЕТОЙ МЕТКОЙ
Слушай, крупнобуквенный, а это ты программистишку форсишь, или вы на пару сычуете.
Как хочешь. Если у тебя типовая задача - бегать по массиву, то ок. У меня обычно количество итераций в цикле предскзать нельзя, поэтому - бесконечный цикл, в нем куча логики и условий, какждое из которых может выполнить break\continue\return. Ну или ексепшн выкинуть можно. Да и вобще я к всяким нововведениям скептически отношусь. Чем меньше синтаксических нагромождений в языке, тем больше программмист уделяет внимния алгоритму, вместо поиска наиболее подходящего синтсахара.
>У меня обычно количество итераций в цикле предскзать нельзя
while () {} / do {} while ();
>поэтому - бесконечный цикл, в нем куча логики и условий, какждое из которых может выполнить break\continue\return
Откуда ж вы блядь такие берётесь. Цикл фор чем хорош, что у него есть явно выраженное пост-условие. Никто не обязывает тебя выражать его в виде инкремента счётчика, можешь хоть вызов функции туда повесить. Равно как и первое условие цикла for это что угодно, необязательно определение переменной.
>У меня обычно количество итераций в цикле предскзать нельзя, поэтому - бесконечный цикл, в нем куча логики и условий, какждое из которых может выполнить break\continue\return. Ну или ексепшн выкинуть можно.
У кого-то проблемы с дизайном и декомпозицией кода?
ВЫХОДНОЕ УСЛОВИЕ НЕУДОБНО РАСПОЛЖЕНА, ОБЫЧНО ТРЕБУЕТСЯ ВЫХОД ИЗ СЕРЕДИНЫ ЦИКЛА А НЕ ИЗ НАЧАЛА ИЛИ ИЗ КОНЦА
ПРИЧЕМ ПО МЕРЕ РАЗВИТЯ ПРОГРАММЫ ВСЕ МОЖЕТ ПОМЕНЯТСЯ И ПОТОМУ ЛУЧШЕ СРАЗУ НЕ ДУМАЯ НАЧАТЬ С БЕСКОНЕСНОГО ЦЫКЛА
Ты читать-то умеешь? Тебе достаточно одно условия на выход из цикла и одного постусловия? Можешь повесить целый вызов функции? Охуеть просто.
>У кого-то проблемы с дизайном и декомпозицией кода?
Пока не замечал. А что?
class ClassWithConstructor {
public:
ClassWithConstructor(float parameter): object(parameter) {}
private:
AnotherClass object;
};
Ты рефакторить код умеешь? Очевидно, у тебя возможны две ситуации:
1) единоразово исполняемое в скоупе действие, основное условие (из многих), чётко отделяемое постусловие цикла -- цикл for () {}
2) основное условие (из многих) -- циклы while () {} / do {} while ();
Кто-то, кажется, не умеет разбивать код на функции и вообще формулировать свои мысли в коде.
>основное условие
Оперируешь абстрактынми терминами, при этом не привел определнения основного условия и ряда объективных критериев его выбора. У нас за такое сразу нахуй посылают.
>чётко отделяемое постусловие цикла
Обычно это изменение счетчика\индеркса\итератора. Отлично подходит для перебора массивов и направленных структур данных. И блять, я писал об этом выше. И для этого конструкция for как раз и была введена. Также как сейчас добавляют всякие foreach-и и range-base for-ы и прочее.
class A
{
public:
A(const char& s);
A& operator+(A& b);
}
void f(A& x) { }
int main()
{
f("Hello" + "World");
}
проще говоря, как замутить автоматическое преобразование char& к A?
NOUP
A() + "hello" + "world". Только так. Ну а далее или оператор приведения типа, или operator+ принимающий сишную строку. Вроде так. Но основное - это A() + "hello" + "world".
Нельзя так, если к классу А прибавлять строку то он автоматически преобразует строку в А, но сразу два слагаемых он не преjбразует. Алсо будет же память утекать.
В каком месте, там все на стеке.
[code lang="cpp"]A(const char* s)[/code]
Есть. Не страдай хуйней.
Лена хороша как материал для ньюфагов, потому что у нее дохуя маленьких статей, посвященных какой-то одной теме и запиленных на основе прочитанных ею же книг. Да, статьи, где она выражает свое имхо - говно. Да, не стоит воспринимать написанный ею код как что-то хорошее. Да, прочитать литературу из оппоста гораздо лучше и полезнее. Но в качестве сборника кратких выжимок по отдельным темам для чайников я ничего лучше Лены не видел. Такие дела.
слоуответ от опа
Когда ты создаешь переменную примитивного типа (например, int), ты пишешь int a = 1. Здесь никакого конструктора не нужно, просто создаешь и инициализируешь. В случае сложного класса может быть необходимо выполнить какие-то дополнительные действия (например, зарегистрировать созданный объект в списке всех объектов программы или типа того). Конструктор гарантированно вызывается при создании объекта класса и подходит для обеих целей - в его теле ты можешь проинициализировать члены-данные и выполнить вообще любой код, в частности, вызвать другие методы (например, передать в перечень всех объектов указатель на только что созданного себя) этого и других классов.
>ты можешь проинициализировать члены-данные и выполнить вообще любой код
А почему нельзя просто реализовать метод, который будет это все делать и вызвать его явным образом.
Чтобы не забыть его вызвать, например. Существует куча ситуаций, когда объект создается неявно (например, его возвращает функция), и ты легко можешь забыть, что после вызова такой функции нужно вызывать сразу и твой метод. Да и силы это экономит, вместо того, чтобы писать каждый раз, пишешь один раз. Ну а вообще твой вариант тоже используется, просто довольно редко. Например, некоторые контейнеры (типа std::future) требуют, чтобы объект, который они хранят, можно было создать без инициализации (т.е. чтобы у него был конструктор по умолчанию). И инициализируется все уже после конструирования, отдельным методом.
Второй вопрос: я путаюсь в большом количестве h и cpp файлов. Можно это как-то распихать по папкам? Наподобие пакетов в java. Пишу в VC
И третий вопрос: я пишу небольшую игульку всегда при обучении новому языку так делаю, и память вроде не течет... Использую Visual Leak Detector. Может ли быть так, что он мне пиздит и все на самом деле плохо?
>не забыть его вызвать
>силы это экономит
То есть, это не часть ООП идеологии\парадигмы, необходимая для каких-нибудь абстракций\инкапсуляций, а чтобы не забывать функцию дергать?
1. См. оппост:
>Учимся не писать говнокод
2. Разумеется. Распихиваешь файлы по папкам. Дальше в свойствах проекта: Свойства конфигурации - C/C++ - Дополнительные каталоги включаемых файлов. Добавляешь туда все папки с .h, а сами файлы включаешь в проект (слева - Заголовочные файлы - Добавить - Существующий элемент). .cpp достаточно просто добавить в проект (как заголовочные, но тыкать в фильтр "Файлы исходного кода"). Все, после этого можно твои заголовки подключать в угловых скобках, типа #include <TvoyaMamka.h>. Исходники сами скомпилируются и скомпонуются.
3. Если ты не используешь голые malloc/free, то точно нет. Если используешь, то хуй знает, но скорее всего тоже нет. Вообще, vld это классная вещь, я бы не волновался, что он может напиздеть. Если таки играет очко, используй RAII вместо прямого выделения памяти и волноваться точно будет не о чем.
Неет, это часть идеологии хотя бы потому, что у любого класса будет как минимум один конструктор если ты ничего не написал, то сгенерируется пустой конструктор по умолчанию. При создании объекта должен быть вызван какой-то конструктор, без исключений. Ты можешь написать TvoyaMamka::TvoyaMamka () = delete; и он не сгенерируется, но тогда ты не сможешь создать ни одного объекта класса. На самом деле только поехавший не стал бы использовать конструкторы, даже если бы они не были обязательными, потому что это адски удобно. Ты один раз объясняешь, что делать при создании объекта, и больше не забиваешь этим мозг, воспринимаешь его как обычный примитивный тип, если угодно. И пишешь в духе TvoyaMamka elena_mikhailovna = 90;, а что там у нее будет 90 - рост, вес или все сразу - тебя уже не должно ебать. Инкапсуляция свойств как она есть.
Спасибо, добра тебе
>а что там у нее будет 90 - рост, вес или все сразу - тебя уже не должно ебать.
Но подожди, если я не буду знать, что означают параметры конструктора, откуда я пойму какими значениями их надо заполнять?
>Оперируешь абстрактынми терминами, при этом не привел определнения основного условия и ряда объективных критериев его выбора. У нас за такое сразу нахуй посылают.
Зависит от задачи, очевидно.
>Обычно это изменение счетчика\индеркса\итератора. Отлично подходит для перебора массивов и направленных структур данных.
Обычно да, но не только, блядь, НО НЕ ТОЛЬКО! У меня, например, постусловием идёт вывод информации в одной из задач.
И, кстати, читаемость кода только повысилась, он ужался и стал компактным.
>>504045
Да её даже в комментах собственные друзья хуесосят. На мой взгляд, стоит начинать с учебников. Не можешь осилить учебники и упражнения из них - сразу иди нахуй. А то начитаются Алёны и потом говнокод вопреки стандарту пишут.
>рост, вес или все сразу - тебя уже не должно ебать. Инкапсуляция свойств как она есть.
>>504194
>Из документации?
То есть ООП, для того, чтобы из исходников было непонятно что по чем, и поэтому надо читать документацию?
>>504228
>НО НЕ ТОЛЬКО! У меня, например, постусловием идёт вывод информации в одной из задач.
Ну вообще только. Из семантики же следует: (начальное значение;условие прерывания;изменение состояния).
Ты, вероятно, будешь удивлён, но даже при очень придирчивых настройках компилятора тебе даже предупреждения не выдаст. Всё компилируется и работает.
>То есть ООП, для того, чтобы из исходников было непонятно что по чем, и поэтому надо читать документацию?
Че ты все к ООП цепляешься? Ты спросил "А с какими это мне параметрами надо функцию вызвать?" я ответил.
Не нравится документация? Читай заголовок, типа
class TvoyaMamka(int SkolkoRazEeEbali) {...}
Обычно стараются сущностям давать имена, отражающие их суть.
>Местоположение\tРедмонд, Соединенные Штаты
А где ты находишься, мм?)) Может быть Silicon Valley?
>На мой взгляд, стоит начинать с учебников
Полностью согласен. Но давным давно, когда я учился на втором курсе ВМК и часто проебывал восхитительные семинары по крестам, а из книжек времени хватало только на Шилдта - вот тогда пару раз мне ее статьи сильно пригодились тому що экономили время. А потом уже я прочитал много умных книжек и ужаснулся, вновь наткнувшись на них. А ньюфагам должно быть полезно, если только они не будут как макаки все копировать.
А еще она занимается разработкой игор, имеет личинок и мужа с большим членом. Мечта местного контингента так жить просто, с учетом склонности к байтоебскому мазохизму.
>мужа с большим членом
У неё муж негр чтоли?
По блогу особо не копался.
По делу, воспитанные интеллектуало-няши уёбывают отсюда в далёкие края, и там обустраиваются. Я не верю, что на должность кококодера при зарплате 10к$ возьмут пизду ради пизды. На этом тему стоит закрыть, пока опять срачь не начался.
Я в замешательстве - начал читать Страуструпа про С++, а тут мне аноны подказывают что ++ говно и лучше учить шарп или яваскрипт...
>Вообще, vld это классная вещь, я бы не волновался
Ну ахуеть. Поставил я этот vld, прописал пути, заинклудил, сделал каноническую утечку
int *pointer = NULL;
for( int i = 0; i < 10; i++ ) {pointer = new int;}
delete [] pointer;
И в окне вывода нихуя. Думаю чет не работает, наверно. Прописал в конфиге у vld вывод в файл. Он мне туда вывел
>Visual Leak Detector Version 2.3 installed.
>Outputting the report to the debugger and to (путь к проекту)\memory_leak_report.txt
>No memory leaks detected.
>Visual Leak Detector is now exiting.
И где что не так?
Выбирай технологию блять исходя из того, какая тебе больше нравится, сколько вакансий в твоём городе по ней. Аноны тут тебе такого нарасказывают, окажется, что вообще нихуя учить не надо
Ну, я не совсем хотел язык для работы, сколько хотел делать игры, у меня есть куча кириллоидей.
Какой язык выбрать?
Ну хуй знает. Поставил я этот vld, прописал пути, заинклудил, сделал каноническую утечку
Visual Leak Detector detected 9 memory leaks (360 bytes).
Largest number used: 2160 bytes.
Total allocations: 2312 bytes.
Visual Leak Detector is now exiting.
Для игор? Что именно ты хочешь ПИСАТЬ? Программировать графон? Тогда кресты адназначна.
Кресты для ГРАФОНА не нужны. То, для чего кресты применяются в игростроении, уже давно написано.
Если не собираешся делать шутаны, то бери юнити (а там шарп). С ним куча людей к успеху пришли.
Ну не на ассемблере же писать...?
Да, и если углублятся, тогда уже лучше сделать мод на уже готовую игру - что меня не устраивает.
>Ну не на ассемблере же писать...?
Тоже чужие наработки. Начни с проектирования собственного железа.
А с какого начать?
Да, и я читаю что в разные конторы, которые делают игры, требуются специалисты по С++.
Ну без использования сторонних библиотек/фреймворков ты нихуя не напишешь, даже для дварффортреса нужно подключать ncurses или как Тоади пердолится с опенгл. Проще всего начать с подбора фрейморка и использовать его язык. А у тебя какие-то странные предубеждения.
Итак, ты можешь взять с++ и какую-нибудь библиотеку, например sfml, и начать велосипедить. Потому что ты не быдла, только школьники используют юнити!
А через некоторое время тебя это заебёт и ты станешь использовать юнити. сужу по своему опыту
В чем суть юнити?
Я всегда думал что это как редактор к варкрафту, только с намного большими возможностями, но всё равно недостаточными?
К тому же, я слышал что там можно писать только на С#.
Игровой движок. Что хочешь, то и сделаешь.
И на C# очень приятно и легко писать в отличие от крестов
1. Бери https://code.google.com/p/blackthorn-engine-3d/
2. разбирайся
3. допиливай
4. делай свою йобу
5. ???
6. ВЫГОДА
Как раз и проектировать научишься.
Я думаю тебе все равно что использовать. На простых вещах разницы нет. Хоть питон бери. Можешь плюсы попробывать, как анон выше писал ищи книгу "SFML Game Development.pdf" и ебашь по ней. Если обосрешся с подключением sfml ищи что-то проще. Но это уже наверное не плюсы, что-то не вспоминаю ниодной просто подключаемой библиотеки. Раньше тебе можно было бы graphics.h обойтись, но сейчас ее наверное хуй найдешь.
>sfml
Как я понял это что-то типа опенгл или директикс?
Почему сразу их не использовать, например?
>намного большими возможностями, но всё равно недостаточными
Сities: Skylines, Kerbal Space Program, Endless Legend, Infactory демиурги, лол, какой это год был-то? это недостаточные возможности?
> Почему сразу их не использовать, например?
По той же причине по которой не используют ассемблер. sfml обертка над opengl.
Для шарпа есть еще monogame.
А для крестов не так уж и много игровых движков/библиотек с хорошей документацией. Так что выбор на самом деле невелик. А на OpenGL писать игры не самый лучший вариант, он тебе нужен, если только сам движкописательством хочешь заниматься или интересует программирование графики.
А самому нереально сделать такое?
Вообще, я хотел сделать игру с крутым ИИ, что-то похожее на ДФ.
И еще, я видел как-то скриншот - какие-то танки в псевдографике, там всё было выделено зелёными линиями, и полигонов было очень мало. Я думаю такую игру просто написать, вот это я бы еще хотел попробовать написать.
Понятно. Закатывай губу, бери любой язык высокоуровневый, не кресты. питон пойдет, бери любую библиотечку для работы с графикой и пили змейку, тетрис-хуетрис. Потом что-нибудь посложнее, ещё можешь поковырять готовые 2д-движки.
Потому, блять. Без элементарных навыков единственное, что у тебя получится, - участвовать в срачах на /gd
У меня есть навыки работы в пхп/скл (хтмл, цсс), немного яваскрипта (не особо в нём разбирался, но писал простенькие фишечки, типа открыть, закрыть комментарии етц.).
И вот уже где-то месяц я мечусь в поисках того что мне нужно - с чего начать.
Немного почитал про С++, потом мне сказали что это говно, все не любят этот язык и подвергают жесточайшей критике. Что число программистов и вакансий на этот язык сокращается.
Попробовал Питон, но пишут что он слишком простой, и сложные программы (типа игр) на нём не сделать.
В общем, сам не знаю что делать.
>В общем, сам не знаю что делать.
Что-что... вкатываться постепенно.
Питон отлично подойдет: быстрее освоишь, не будешь тратить время на малозначимые нюансы, коих в крестах слишком много, => быстрее прийдешь к результату.
Но на питоне же никто не пилит игры сложнее змейки?
У меня от твоего поста появилось чувство:
>быстрее прийдешь к результату
Будто под результатом ты имеешь ввиду что я на всё забью и дропну.
Проблема не в том, что питон прост, проблема в скорости его работы, поэтому круизис на нем никто не пилит.
Ты хочешь работать в геймдеве или хочешь сделать игру?
Если первое, тогда кресты.
С++ используется в разработке "серьезных" игр из-за скорости и производительности. Но разработка на нем более медленная и сложная из-а особенностей языка. Для проекта в одиночку это весьма важный момент. Я сомневаюсь, что при разработке твоих игр ты столкнешься с проблемами, которые и вынуждают использовать с++
Майнкрафт вон на тормозной джаве написан и норм же.
Следует выбирать то, что удобно.
Можешь еще в сторону haxe поглядеть я на нем от скуки, используя движок haxeflixel платформер за два дня написал. Самое то для начинающего инди. Правда haxe малопопулярен и никому особенно-то не нужен.
Пусть начнет с создания собственной вселенной для начала.
Разберешься - сменишь инструмент на более подходящий, если в том будет необходимость.
А пока больше вероятность, что ты дропнешь где-то между хелловорлдом на плюсах и змейкой на них же.
Стоп, т.е. на питоне я смогу написать тоже самое что и на С++, только это просто будет жрать больше ресурсов?
И медленнее работать? Да. Но для простых игр это не сильно критично. Ну и сильно влияет вопрос кривости рук
>ДФ написан на плюсах, а при крепости в 100+ бород тормозит на компе, который Крузис потянет
А как же все эти библиотеки - опенглы и sfml? Они же, вроде, только для низкоуровневых языков программирования? Или как?
Не понял вопроса. Для питона есть свои библиотеки. Билдинги к сфмл есть к самым различным языкам, но либа эта крестовая и обычно на крестах под нее пишут.
>Или лучше С++
Не лучше и не хуже. Я как-то ради лулзов писал игру на go, хотя он нихуя для этого не предназначен.
Ты блять, какой-то неуверенный, но ладно, так и быть, я разрешаю тебе выбрать питон.
Выбери уже что-нибудь, главное не сиди и не теряй время.
ЗА ДЕНЬГИ
Зеленый ебальник ему набить надо, а не скиллы.
Да он с двача выйти не может.
Всё, тогда учу С++
пили сюда пример своего while-цикла, поржем
Значит, утечки нет. Он же диагностирует их по факту, а не гипотетически возможные по стандарту. Видимо, в твоем случае new выделит им место последовательно, а потом delete [] простит косяк и удалит все. Вот он и не кукарекает.
>>504479
Так может у тебя еще утечки есть. Сделай main с утечкой и ничего больше. Ну и энивей для меня, например, его результат бинарный - либо есть утечки, либо нет, а на количество насрать, энивей исправлять же.
Нет.
Потому что писал еблан. Дай школьнику кресты, он там тебе такого понапишет с параллельными массивами и утечками на каждом шаге. Язык это не панацея же, а необходимое условие.
Показывай давай.
Помимо книг из оппоста:
Р. Мартин нет, петушок, это другой Мартин - Идеальный программист.
Э. Хант, Д. Томас - Программист-прагматик.
>Мартин
And who are you,
The junior said,
That you call my code slow?
Only a slave
With a different pay -
That's all the truth I know.
>>504727
Так, Тоад далеко не школьник, он учёный и имеет какие-то там дипломы за знание математики.
>Так, Тоад далеко не школьник, он учёный и имеет какие-то там дипломы за знание математики.
Дык, учёный - не крестозадрот. Ему, как и любому другому нормальному человеку, ценящему своё время, легче написать простой и понятный код, чем ебаться с корявостью языка, переусложняя код на каждый чих. А то, что результат получился малоэффективный, - следствие низкоуровневости языка. На ассемблере получилось бы ещё более тормозное говно.
Ага.
[code]1. template<typename T> void ft(T);
2. template<> void ft<int>(int);
3. void ft(int);[/code]
1 — шаблон, 2 — явная специализация шаблона, 3 — просто функция.
К примеру, можно использовать 1 и 2 или 1 и 3, то есть выбор между явной специализацией шаблона и просто функцией. Какие преимущества есть у явной специализации перед простой функцией, помимо того, что шаблон создаётся только тогда, когда нужен, а функция — всегда?
В 90% случаев continue/break являются индикатором плохого дизайна. Понятное дело, что если ты там поддерживаешь легаси с функциями длинной по 500 строк, то уже похуй и можно использовать что угодно, как и в случае, если тебе надо быстро-быстро накидать чтобработало и больше никогда его не открывать. В остальных же случаях всякие goto/continue/break, множественные ретёрны, длинющие функции-листинги, глубокие уровни вложенности и т.д. - запах говнокода, который бездумно писали не проведя нормальную объектную/структурную декомпозицию. Есть конечно ебанутые алгоритмы, которые по-другому не запилишь но как правило такие места встречаются редко.
Нужно отдавать себе отчёт в том, что это грубый сontrol flow, который понижает читабельность кода и размывает его консистентность, и стараться пересмотреть написанное каждый раз когда возникает желание их использовать.
А ты не путаешь явную специализацию с явным созданием экземпляра шаблона? Иначе я вообще не понимаю смысла в явной специализации. Или это я попутал…
>>504862
>Какие преимущества есть у явной специализации перед простой функцией, помимо того, что шаблон создаётся только тогда, когда нужен, а функция — всегда?
>шаблон создаётся
Правильнее, конечно, экземпляр шаблона.
В любом случае какие профиты-то?
На мой ньюфаньский взгляд читается очень легко. Хотя, наверно, можно вместо if (ProxyObject == null) return; и прочего писать что-то типа if (ProxyObject == null) {...}. То есть вкладывать всю остальную программу в них. Однако я не уверен, что это будет читабельнее.
>Однако я не уверен, что это будет читабельнее.
Их надо вынести в отдельную функцию. Появились же вложенные функции в плюсах.
>Например то где пояснят отличи sort и qsort. Что посоветуете?
"Многознанiе уму не научаетъ" (c)
Пиши код.
>2 последних пика
>по стандартной библиотеке
>Прата
Читать Прата после Страуструпа — это мощно. У него же идёт введение в язык с нуля. Загляни в оп-пост же.
Поясни тогда за случаи:
1. Метод получает параметр, который ему не нравится, и это видно сразу в начале метода например, nullptr. При этом ситуация недостаточно плоха, чтобы кинуть исключение, следует просто ничего не делать. Как по-твоему здесь сделать лучше, чем сразу return?
2.
[code = "cpp"]
Momma getYourMomma (size_t height, size_t weight)
{
\tstring request = "method=getMomma&height=" + std::to_string (height) + "&weight=" + std::to_string (weight);
\tfor (;;)
\t{
\t\tauto response = getResponse (request + "&nonce=" + std::to_string (getTime ()));
\t\tif (response.hui_sosi)
\t\t\tcontinue;
\t\treturn response;
\t}
}
[/code]
Как в этой ситуации быть с твоей точки зрения? Если невозвращение сервером корректной мамки - это обычное дело, то исключения все замедлят. Вычислить один раз строку запроса и крутить в цикле только сам запрос нельзя из-за параметра nonce. Использовать do-while плохо из-за тот, что while легко спутать с началом нового цикла. Возвращать некорректную мамку наружу и вызывать метод, пока он не отдаст нормальную - плохо, клиент метода не хочет ничего проверять, он хочет получить корректную мамашу. Делать для этого второй метод-прослойку - чрезмерное запутывание кода.
>Нужно отдавать себе отчёт в том, что это грубый сontrol flow, который понижает читабельность кода и размывает его консистентность, и стараться пересмотреть написанное каждый раз когда возникает желание их использовать.
Очнитесь товарисч инженегр.
Двадцать лет мы двигаем «break» в конец цикла и «continue» в начало и у нас всё работает!
А если упоротые выскакивания из середины цикла понижают читабельность кода, то только у вас.
>Николаи Джоссатис - C++. Стандартная библиотека
Случай, братюнь, ты охуел штоле не читать оппост, блядь? Я старался, выбирал самые годные книги, собирал ссылки, чтобы анону искать не нужно было. Читай. Читай оппост до конца, блядь. Не хочу. Хочу жрать говно.
[code lang="cpp"]
while (true)
{
\tcontinue;
\t//body
\tbreak;
}
[/code]
>всё работает
Я бы даже сказал всегда работает, если вы понимаете, о чем я.
Я бы не назвал книгу Джоссатиса сложной. Она объемная просто, тому що STL большая. И в ней новейшие сведения вплоть до C++14, в отличие от.
Бампану вопросик.
>И в ней новейшие сведения вплоть до C++14
Мы точно про одну книгу говорим? Она же 2004ого года.
>Если невозвращение сервером корректной мамки - это обычное дело, то исключения все замедлят.
И всё же исключения. Но не
throw new Excpetion(ERR_OBOSRATUSHKI_OBTEKATUSHKI_SHOPESDEATH);
А вот так
throw AbstractSingletonProxyObosramsException;
Константу бросить, короче. Тогда тормозить не будет.
Будет существенно тормозить из-за невозможности объявить метод как noexcept и генерации лишнего кода обработчика.
На самом деле я хотел воткнуть новое издание в оппост, но не смог найти, где я его взял. А ргхост в шапке быстро протухнет.
Да ты охуел. Если у меня маленький метод, который в десять строчек скачивает мамку, я должен, блядь, генерить обработчик, который в три раза больше займет в VC, да еще и вызываться будет десять раз на один нормальный возврат мамки? Увольте-с, continue здесь меньшее зло.
Вот залил. Храниться вечно. Но можно настроить и по другому если надо.
http://my-files.ru/cdm4zk
my-files.ru/Download/cdm4zk/%d0%94%d0%b6%d0%be%d1%81%d0%b0%d1%82%d1%82%d0%b8%d1%81%20%d0%9d.%d0%9c.%20-%20%d0%a1%d1%82%d0%b0%d0%bd%d0%b4%d0%b0%d1%80%d1%82%d0%bd%d0%b0%d1%8f%20%d0%b1%d0%b8%d0%b1%d0%bb%d0%b8%d0%be%d1%82%d0%b5%d0%ba%d0%b0%20C%20%20.%20%d0%a1%d0%bf%d1%80%d0%b0%d0%b2%d0%be%d1%87%d0%bd%d0%be%d0%b5%20%d1%80%d1%83%d0%ba%d0%be%d0%b2%d0%be%d0%b4%d1%81%d1%82%d0%b2%d0%be%20-%202014.djvu
http://my-files.ru/Download/cdm4zk/Джосаттис Н.М. - Стандартная библиотека C . Справочное руководство - 2014.djvu
Нечто вроде
[code = "rust"]
repeat(request).map(|req| get_responce(req + "&nonce=" + get_time().to_string())).find(|ref r| r.is_ok()).unwrap()
[/code]
у вас в плюсах не принято?
мимопроходил
>Какие преимущества есть у явной специализации перед простой функцией, помимо того, что шаблон создаётся только тогда, когда нужен, а функция — всегда?
Ещё одна попытка.
Гугл -> visual studio 2013 (или даже 2015) -> первая ссылка -> ??? -> profit
Вот ссылка. Он тебе не будет насильно пихать гуй и виндосовскую библиотеку.
http://sourceforge.net/projects/codeblocks/files/Binaries/13.12/Windows/codeblocks-13.12mingw-setup-TDM-GCC-481.exe/download
У нас есть do {response=getResponse (request + "&nonce=" + std::to_string (getTime ()))} while (!response.hui_sosi), но это нечитаемо же. И масштабируется плохо.
Ну короче идешь в comp.lang.c++ и спрашиваешь, файлы тоже где-то там лежат. Компилятор-то Бьерн периодически выкладывает туда. В интернете я как-то видел архив с компилятором, но чего-то не могу найти.
Кто юзает кодблокс - поясните, как тут компилировать программы?
ВОт, копировал простейший код, а как его исполнить?
>Code::Blocks 13.12 is here!
>Friday, 27 December 2013 20:00
Он таки умер?
Значение.
Если не меняешь изнутри - константную ссылку, значение. Если меняешь - указатель. Так будет заметнее, что меняешь.
Если не нужен null, то используй ссылки
Мутабельная ссылка - это бомба, нужно использовать указатели, там сразу видно, что что-то не то.
Что сказать-то хотел? Вообще не использовать ссылки для изменения значений?
Он странный какой-то. Используй ссылки как можно чаще. А константные ещё чаще.
По возможности вообще не менять значения входных параметров, старайся делать функции как можно более чистыми.
- На работу! Чисти функцию, блядь! На! Чисти функцию!
- Чем, указателями, что ли, я буду?
- Чисти функцию! Да садись уже! Садись. Чисти!
- Блядь...
- Чтобы побочных эффектов не было!
- Как я буду на крестах-то чистить?
- Чисти!
- Покажи мне.
- Чисти!
<тимлид уходит>
- Епты. Блядь... Говно, блядь... Как в нем чистить, еб твою мать... Все ебанулись. Бля... Епта...
<пытается передать параметры через константные указатели, в это время тимлид возвращается>
- Чисти, чисти, сука. <достает хаскель> Вот как, блядь, нужно чистить,вот,быстро. Быстро. Раз-раз! Чисти, чисти, чисти-чис-чис-чиж-чж-чижь! Чисти! Говно! Чисти!
- Бля, у тебя получается классно, давай!
- Давай! Работай!
- Не буду я в этом писать, блядь! Не буду я!
- Пошел нахуй тогда отсюда, пошел! Блядь, ничего не можешь сделать, пошел нахуй, говно!
Тебе зачем? Пощупать хватит и триала. На постоянной основе пользуюйся clang-toolkit и cppcheck
Мне прельстива его заточенность под студию. Для cppcheck тоже вроде как есть плагин, но он, насколько я понял, нерабочий то ли он ничего не показывает, пока полностью не проверит весь проект, то ли багнутый, но когда тыкаешь запуск, то нихуя не выводится. А standalone-версия у него вроде нормальная, но ее же вечно забываешь запустить, а я хотет, чтобы сразу можно было чекать, при написании кода, а не переключаться хуй знает куда.
Добавь external tool, для папки и текущего файла. 3 минуты и у тебя рабочие тулы
А если у меня цель функции -- изменить значение по ссылке? Например, потому что я не хочу копировать параметр, чтобы потом изменить его один раз, чтобы потом вернуть его как результат функции, чтобы потом результат функции скопировался в ту переменную, которую я до этого передавал как входной параметр?
void функции -- это вообще лучшее, что придумал Иисус. Потому что они учат работать с ссылками, т.е. void функции -- это нечто, что надругается над данными извне.
А ещё функция может быть предназначена для того, чтобы изменить например два инта и один чар, и что теперь, по каждому чиху Struct лепить?
Блядь,отписался без сажи в Алёна-треде. Всё, я зашкварен.
>изменить например два инта и один чар, и что теперь, по каждому чиху Struct лепить?
Нет конечно, это же С++ тред. Ты должен спроектировать интерфейс, создать дочерний класс, с кучей конструкторов на все случаи жизни, перегруженными операторами, ну и конечно обернуть все в шаблоны. Только идиот будет от всего этого отказываться - упрощает кодирование, сокращает время разработки и пр. преимущества.
Изменяй по указателю. Тогда программист увидит foo(&x) и поймет, что x, скорее всего, меняется.
>А ещё функция может быть предназначена для того, чтобы изменить например два инта и один чар, и что теперь, по каждому чиху Struct лепить?
Для двух интов и чара ты можешь и std::tuple вернуть, тогда не придется заставлять пользователя создавать int tmp1 там, где ему не надо.
1. Преимущественно следует делать через указатели, это верно.
2. Иногда использование ссылок предпочтительнее. В частности, когда в метод метод может не просто изменять аргумент, а портить его, перемещая. Если ты в любом случае готовишь временный prvalue-объект (напрямую или делаешь его с помощью std::move), то использование мутабельной rvalue reference в таком методе предпочтительнее использования указателя, ибо с указателями создание объекта для передачи придется отделять от взятия адреса для передачи в метод. Такой способ использования ссылок-параметров не даст выстрелить себе в ногу, потому что для вызова над ценным объектом энивей придется явно указать std::move для него.
3. Проблема преувеличена даже в случае обычной ссылки. Если метод возвращает void и имеет имя getTvoyaMamka, то вряд ли его используют в надежде, что он ничего не сделает с параметрами. Нужно думать головой, и все будет хорошо.
Рассмешил, пес.
Заебал, скачай Dev-c++ и не еби мозги. А по факту посмотри видео и с помощью блокнота и конскольки собери хоть одну программу.
Ананасы, нид халп. Си++ или С
for (auto & current : array) current /= *std::min_element (std::begin (array), std::end (array));
Пасяб
Ну хуй знает. Я как раз сегодня попробовал в перенос проекта на RC, оказалось, что это предрелизное говно кишит багами, блядь. Не может распарсить инициализацию с шаблонами вне конструктора в духе члена TvoyaMamka mamka = Mamkogenerator <TvoyaMamka>::getObject ();. Какие-то охуительные утечки при создании std::thread, причем вообще на стеке. Обоих багов в 13 релизной не было, ну я и вернулся на нее, пока не поздно. Ждем RTM короче.
cv::Mat dst;
cv::dft(q, dst, cv::DFT_SCALE|cv::DFT_COMPLEX_OUTPUT);
Тип q - матрица (n,1) на. В dst лежат случайные цифры (23, миллион, -inf). Каждый раз разные. Явно в памяти какая-то лажа. Но как такое может быть?
Ну, дружочек, расшифровывай тогда. Мне-то откуда знать, что там у тебя за cv::Mat.
Если ты не знаешь, что это, ты вряд ли ответишь на мой вопрос. Вообще это больше крик души.
Я с OpenCV знаком только на универском уровне, распознавание монеток и вот это все. Когда начинается байтоебство с возвратом говна через параметры и ФЛАГАМИ | НАСТРОЙКАМИ, мне сразу хочется взять и уебать.
Да тут не важно в общем-то, OpenCV это или нет. Явно у входного параметра какой-то кривой форма. Может его транспонировать, лол.
Ты для начала тогда глянь, эта хуета в dst, она меняется после фурьеризации, или это просто мусор из-за того, что не инициализировано. Вообще, запусти отладку, залезь поглубже и смотри, что там происходит же.
Драсте, выучил я тут, короче, похапе и застрял на том, что для дальнейшей практики нужно покупать ебучий хост. К тому же в вакансиях на фрилансе требуется целая хуева туча каких-то фреймворков и MVC. Решил выучить язык с более доступной средой разработки - кресты. Вроде он котируется, как сложный и вакансии на нем должны быть. Поясните за фриланс на крестах желательно на елансе и прочих зарубежных фирмах. Какое должно быть портфолио и все такое?
Фриланс на крестах возможен, но порог вхождения очень высокий. Если ты не способен разобраться в проблемой бесплатного хостинга, то это явно не для тебя.
Я могу разобраться с проблемой бесплатного хостинга, но там нет табблицы ИННОБ дб, а платить штуку за три месяца на платном только чтобы ее выдрочить, я не собираюсь.
Расскажи подробнее про портфолио и хуйню, которую нужно наклепать, чтобы работать на крестах на фрилансе.
числа от 0 до 23?
Стив Макконнелл - Совершенный код. Там не про детали проектирования и тем более не про синтаксис крестов, а общие рекомендации, как улучшить качество кода, в применении к любому языку.
Используй container.at () вместо container [] жи.
Если для тебя это "и все", то да, и все. Но вообще это если у тебя вопрос стоит о "а фрилансе требуется целая хуева туча каких-то фреймворков и MVC", то это нихуя не и все. Ты документацию на llvm видел?
Это тоже может быть полезно, зависит от склада мышления.
в том, что я настолько туп, что не могу и не хочу настраивать денвер или сам пхп.
Тогда ты не сможешь в фриланс на крестах. Попробуй во фриланс на экселе/vb (я не смеюсь, за это тоже платят).
Нет, я постоянно слышу про кресты или шарп. Так что я выбираю между ними.
Но вижуал бейсик я себе уже установил, какие могут тут возникнуть заморочки со средой йопта?
Так проблемы не со средой, а с тобой будут. Видишь: ты уже этого не понял. Иди форму в экселе хуярь.
Он похож на зеленого.
Читай, если уверен, что мотивация не пропадет от изложения без щюток, примеров и упражнений.
Undefined?
1>c:\users\администратор\desktop\visual studio 2013\projects\consoleapplication4\consoleapplication4\consoleapplication4.cpp(13): error C2065: cout: необъявленный идентификатор
1>c:\users\администратор\desktop\visual studio 2013\projects\consoleapplication4\consoleapplication4\consoleapplication4.cpp(14): error C2065: cout: необъявленный идентификатор
1>c:\users\администратор\desktop\visual studio 2013\projects\consoleapplication4\consoleapplication4\consoleapplication4.cpp(14): error C2065: endl: необъявленный идентификатор
========== Сборка: успешно: 0, с ошибками: 1, без изменений: 0, пропущено: 0 ==========
Идентификатор объяви
забыл или #include <iostream> или using namespace std;
Ты заебал во все треды срать своим говнокодом. Серьезно, твоя прога вызывает почти физически ощутимое отвращение.
Что значит "данные лежат в массиве"? Ты хочешь умножить вектор на константу? Тогда сделай проход по массиву и умножь на каждый элемент
ДА ЕБАНЫЙ В РОТ ЭТОЙ РАЗМЕТКИ
С первым слоем все ясно: он по дефолту есть там, где нет ничего другого. Последние два тоже -- там нужно по-любому хранить все в отдельном векторе, потому что объектов относительно мало и они все сложные. А вот с промежуточными непонятка.
Самая банальная идея -- хранить просто матрицу X на Y. Но это, мягко говоря, растратно во многих случаях. Например, если у нас 70% воды, то 70% матрицы будут занимать пустые указатели. Таким образом, мы проебываемся и по скорости работы, и по памяти.
Помимо прочего, этот способ начинает косячить, когда поле условно бесконечно. Нужно либо строить более сложную систему с чанками, либо расширять и двигать матрицу, что пиздец всему.
В общем, расскажите, как это делают умные ребята?
В цивилизации разве многослойное поле? Там просто матрица с объектами.
Бесконечная карта - чанки (то есть те же матрицы), процеурная генерация и хранение диффов между сгенерированным и фактически. Майнкрафт, в общем.
Гугли способы представления разреженных массивов. Вкратце: при любом способе хранения, отличном от обычного, скорость доступа будет ухудшена, твоя задача - найти компромисс между скоростью и размером. Например, все ненулевые элементы хранятся в виде красно-черного дерева. Так как оно сбалансированное (оптимальное по глубине), ты будешь быстро (за O (h)) доставать и изменять элементы, удалять медленнее). С матрицей абсолютно то же самое будет, хранишь дерево для каждой строки, например.
В общем, это был баг в opencv.
[code lang="cpp"]
const size_t n = 100;
\tconst size_t k = 2;
\tconst size_t p = 1; //По какой размерности сортируем
\tint m [n][k];
\tint begin = reinterpret_cast <int > (m);
\tstd::stable_sort (begin, begin + n k, [begin, k, p] (const int & first, const int & second)
\t{
\t\treturn ((0 == (&second - &first) % k) && ((&first - (&first - begin) % k + p) < *(&second - (&second - begin) % k + p)));
\t});
[/code]
Почему?
Контекстное меню - code refactoring - rename symbols не работает?
Где-то видел, что у них быстрая вставка только в конец массива. Это так? Насколько будут медленнее, например, .insert(a.begin(), 1234) или .insert(a.begin() + 10, 1234) по сравнению с простым .insert(a.end(), 1234)?
От размера вектора зависит. Относительно того что всатвка вначало медленее вставки в конец это тестить надо. Вставка в середину однозначно медленее, остальное от реализации зависит. К примеру у яблочного NSArray вродебы хитрожопая реализация с быстрой вставкой и в конец и в начало. В середину естественно медленно - масив же сдвигать надо, от этого никуда не денешся. Быстрая вставка в связные списки - но у них свои недостатки.
template <typename T>
class List
{
public:
\tList()
\t{
\t\tT (List<T>::push)() = &List<T>::push_first;
\t}
\tT (push)();
\tT push_first() {}
\tT push_other() {}
};
Прошу прощения за \t
Ты вопрос читал?
Именно.
Если по-простому, то объявляешь указатель как T (List <T>::*ptr) () = &push_first;
Но нормальные посоны давно юзают std::function, в твоем случае это будет выглядеть как std::function <T ()> push { std::bind (&push_first, this) }; Тогда решается проблема с тем, от имени какого объекта ее вызывать.
> metro
> без C#
А как ты себе представляешь шарпоговно без собственно шарпа?
Можешь попробовать Qt, виджеты умеют в нативные элементы на всех 3-х основных платформах. А на Qml можешь вообще что угодно нарисовать.
Ну хуй знает как, может уже библиотеки какие-нибудь завезли. Самому winapi дрочить не хочется, похоже придется на qt все делать
Кажется это то что нужно, спасибо
template<class _Mylist,
class _Base = _Iterator_base0>
class _List_unchecked_const_iterator
: public _Iterator012<bidirectional_iterator_tag,
typename _Mylist::value_type,
typename _Mylist::difference_type,
typename _Mylist::const_pointer,
typename _Mylist::const_reference,
_Base>
Что такое _Mylist::value_type, что передается в этот шаблон?
Я, вот, читаю, но там используется
cin.get();
cin.get();
return 0;
Заместо getch_
Это правильно или книга уже устарела?
Игнорировать.
Спасибо.
Какая ошибка? Как вызываешь? В общем код в студию, что ж вы такие непонятливые
К сожалению сейчас не могу доставить код. Да похуй уже. Лучше метлу буду осваивать.
Ты это я, дрочил 5 лет в универе C/C++, в то время когда одногрупники занимались вебом. Теперь у меня нет постоянной работы, а не постоянная это курсачи и лабы
Имя типа же. Там в описании шаблонного класса list что-то вроде typedef T value_type. Это сделано, чтобы ты мог узнать тип значения после инстанцирования шаблона, написав list <TvoyaMamka>::value_type. Широко использовалось, когда auto не было, и по-другому тип значения, которое ты хочешь создать, часто было не узнать. Еще применяется в метапрограммировании, например, есть куча служебных структур-шаблонов, в которых ничего нет кроме такого typedef. И ты можешь писать std::is_same <MoyaMamka, TvoyaMamka>::value, и типы сравнятся еще на этапе компиляции, а не с лишними тормозами как при использовании typeid.
Поясняю. Автор нормальный, нужно читать самое последнее издание (оно емнип второй половины нулевых). Книги старые, в первых изданиях и не такое встретишь. Далее. Имена с "_" в библиотеках обычно служебные, code style предписывают обычно именовать так приватные члены (с "_" на конце). То, что они доступны - ничего не значит, часто в стандартах ничего про них нет, т.е. интерфейс не гарантируется, и в любой момент разработчик компилятора может что-то поменять внутри так, чтобы не отвалились только нормальные имена. Таким образом, getch_ использовать нежелательно, он просто не предназначен для использования тобой. istream::get () - это ОФФИЦИАЛЬНЫЙ ТМ метод, его использовать можно, но уместность его ограничена. Видишь ли, считывание по одному символу считается дурным тоном из-за того, что тогда резко усложняется возможность автоматической оптимизации ввода автором библиотеки. Ввод работает далеко не последовательно, по факту символы считываются пачками, а ты использованием get() для считывания из файла вставляешь им палки в колеса. Считывание больших кусков по cin >> TvoyaMamka поэтому гораздо предпочтительнее циклов с istream::get (). Но если ты считываешь с экрана именно по одному символу например, у тебя ебанутый текстовый интерфейс (Y/N)?, то можешь делать get (). Хотя все привыкли к ">>" и это все же считается лучшим способом даже для считывания символов по одному, ибо работа не замедляется, писать меньше, а именование универсальное для всех классов operator>> () обычно занимается вводом, а метод можно назвать get (), или getChar (), или zabirayuSimvol (), такое разнообразие отвлекает. И последнее. Использование get () для того, чтобы программа не закрывалась после завершения - это худшее, что ты только вообще мог сделать. Одновременно показывается и то, что ты запускаешь ее мышкой при запуске из консоли весь вывод сохранится и без get (), разумеется, и то, что ты необучаемый и не можешь нагуглить, как узнать о нажатии клавиши без считывания самого символа.
Поясняю. Автор нормальный, нужно читать самое последнее издание (оно емнип второй половины нулевых). Книги старые, в первых изданиях и не такое встретишь. Далее. Имена с "_" в библиотеках обычно служебные, code style предписывают обычно именовать так приватные члены (с "_" на конце). То, что они доступны - ничего не значит, часто в стандартах ничего про них нет, т.е. интерфейс не гарантируется, и в любой момент разработчик компилятора может что-то поменять внутри так, чтобы не отвалились только нормальные имена. Таким образом, getch_ использовать нежелательно, он просто не предназначен для использования тобой. istream::get () - это ОФФИЦИАЛЬНЫЙ ТМ метод, его использовать можно, но уместность его ограничена. Видишь ли, считывание по одному символу считается дурным тоном из-за того, что тогда резко усложняется возможность автоматической оптимизации ввода автором библиотеки. Ввод работает далеко не последовательно, по факту символы считываются пачками, а ты использованием get() для считывания из файла вставляешь им палки в колеса. Считывание больших кусков по cin >> TvoyaMamka поэтому гораздо предпочтительнее циклов с istream::get (). Но если ты считываешь с экрана именно по одному символу например, у тебя ебанутый текстовый интерфейс (Y/N)?, то можешь делать get (). Хотя все привыкли к ">>" и это все же считается лучшим способом даже для считывания символов по одному, ибо работа не замедляется, писать меньше, а именование универсальное для всех классов operator>> () обычно занимается вводом, а метод можно назвать get (), или getChar (), или zabirayuSimvol (), такое разнообразие отвлекает. И последнее. Использование get () для того, чтобы программа не закрывалась после завершения - это худшее, что ты только вообще мог сделать. Одновременно показывается и то, что ты запускаешь ее мышкой при запуске из консоли весь вывод сохранится и без get (), разумеется, и то, что ты необучаемый и не можешь нагуглить, как узнать о нажатии клавиши без считывания самого символа.
В ней тоже используется эта конструкция. Но ладно, раз 2012 год, вроде еще актуально.
Спасибо.
Ну так это костыль для самых маленьких же. Тут либо ты используешь нормальную IDE Visual Studio, либо для своих программ делаешь ожидание нажатия клавиши как полагается, без костылей. Но проблема в том, что Прата пишет книгу для нубов, и оба решения неуместны - попросишь нюфага качать IDE или начнешь объяснять на две страницы, как сделать нормально, а он возьмет и ливнет. Поэтому дается быстрое решение для тех, кто не хочет ничего решать. Ты еще не видел мой учебник по ассемблеру, там вообще давалась распечатка библиотеки ввода-вывода, потому что про это объясняется только в конце книги, а работать с примерами как-то надо, лол.
>Visual Studio
А кодблокс нормальный? Мне понравилось что он не такой громоздкий и не устанавливает гиг дополнительной хуйни.
Даже можно портативным сделать.
Видишь, какой я немодный теперь. emacs+cmake+qtcreator для gui-дебага - идеальная связка для меня.
Ну он годен под стандартные задачи, но если честно, студия настолько оставляет позади по удобству все остальные среды, что я готов ей прощать косяки и посерьезнее гига дополнительной хуйни. Визуальный отладчик с деревом потоков и IntelliSense просто божественны, базарю еще захочешь.
Я вообще кьютом не пользуюсь. QtCreator я использую только как фронтэнд к gdb - он хорошо работает с cmake-проектами, нативный, а не на java писан.
А "текстовый редактор для программирования" - а что еще можно использовать, не IDE же.
Что-то не работает, или у меня руки из жопы, или надо ждать win 10
Есть что по этому поводу почитать? Видел статью на хабре, но там только про ввод/вывод на экран. Если не средствами программ, а средствами системы перенаправить вывод в файл, то результат не измениться?
В llvm он вообще запрещен:
#include <iostream> is Forbidden
The use of #include <iostream> in library files is hereby forbidden, because many common implementations transparently inject a static constructor into every translation unit that includes it.
Note that using the other stream headers (<sstream> for example) is not problematic in this regard — just <iostream>. However, raw_ostream provides various APIs that are better performing for almost every use than std::ostream style APIs.
Note
New code should always use raw_ostream for writing, or the llvm::MemoryBuffer API for reading files.
Просто найди исходники реализации и посмотри, возможно внутри все сделано на старых сишных методах
Ну смотри потоки в C++ типобезопасны, все проверяют за тебя. Быстрее конечно будут работать си методы, т.к. они всю проверку скинули на плечи разработчика. И вот если ты сам будешь делать сложные проверки, то можешь навелосипедить и будет даже хуже.
>типобезопасны
Стоп. Какой с этого профит? В задачах все входные данные корректны. Это значит что он лишний раз проверку делает? Что-то такое подозревал, но разве это единственное отличие? И что можно навелосипедить? Прочитать string как int?
Профит такой, что если ты записываешь сложные структуры, то создаются виртуальные функции, и тебе не надо самому проверять формат ввода + следит за утечкой памяти. Если у тебя все однородно используй из си
Всё понял. Спасибо.
Скажи, как можно реализовать для QGraphicsView (или QGraphicsScene) затемнение по маске? Хочется сделать смену дня и ночи в игруле -- думаю, как бы это реализовать.
Естественно, нужно учитывать и источники освещения, поэтому нужна именно маска, общий способ менять яркость сразу у всей сцены тоже пригодится.
Qt maintaining tool?
Как именно работает ввод с потоков? Скажем, программа получает на вход мегабайт текста. Где этот текст храниться? Могу ли я два раза прочитать одни и те же данные с какого нибудь cin?
Простите если нескладно.
Если сделать функцию int main (int argc, char * argv[]) то бегать по аргументам можно сколько угодно.
Тебе нужен какой-то курс по архитектуре ЭВМ в отрыве от крестов. Обычно же учебная программа в вузах строится так: сначала изучают алгоритмы при помощи высокоуровневого языка у нас паскаль, у них питон, в котором не обязательно вообще знать что-то про память и указатели, не говоря уже про статическую/динамическую/автоматическую память. Потом изучают голую архитектуру ЭВМ и разбирают по частям простейшие программы на ассемблере. И именно в этот момент ты узнаешь про адреса, сегменты данных/команд/кучи, как работает стек, как работает вызов функции и вот это все. Затем изучают, как работает ОС и как она взаимодействует с программами. Здесь про процессы, распределение динамической памяти, разделение процессорного времени между программами, обычно на примере чистого си, потому что он достаточно низкоуровневый, но в отличие от ассемблера можно написать большую программу, не надорвавшись. И вот после того, когда ты все это узнал, ты начинаешь учить кресты. Если приступить к крестам сразу как многие пытаются, то ты будешь все время пытаться использовать его как паскаль/питон, стремясь убежать от непонятных низкоуровневых возможностей. И тогда вся суть крестов теряется, а побочные эффекты в виде множества возможностей выстрелить себе в ногу остаются. Так что либо хотя бы пробегись по всему четырехсеместровому курсу, либо учи питон и не дури. Книги: архитектура и ассемблер Пильщикова (короче) или Юрова (длиннее), операционные системы Таненбаума.
Наоборот, библиотека ввода-вывода си это говняное медленное легаси. Поэтому при работе с большими данными рекомендуется опускать флаг совместимости iostream с ней, ускорение до 10000 раз. Такие дела.
Поток это с точки зрения программы просто файл, который открыт на чтение без произвольного доступа. Соответственно, система имеет право удалить прочитанные символы. Но может и не удалить. Энивей попытки их прочитать второй раз, сдвинув каретку назад это UB.
Твой второй вопрос: ну, например, ты считал их в переменную-строку, теперь символы скопировались в нее и лежат в оперативной памяти. Старые символы в потоке, возможно, удалились. Если ты считал и не схоронил в переменную, то они потеряны.
То есть ничего определенного сказать нельзя?
Если на входе я получу X байт, и сохраню их в какой нибудь переменной, то нельзя точно сказать, сколько памяти будет есть программа, X или 2X байт, так?
Та память, которая, возможно, освободится, не принадлежит программе. Ты не можешь ей управлять, ОС сама очистит ее, если ей понадобится больше места. Так что считай только свои переменные.
Спасибо, это и хотел узнать.
Элегантное решение для синхронизации критическими секциями.
Есть класс КритикалСекшн. У него есть коллекция туплов примерно таких<std::string, size_t count, HANDLE>. Конструктор класса принимает строку. Если нет в коллекции записи с такой строкой, создаёт критическую секцию соответсвтующую, добавляет в коллекцию, на сайз_т делает 1, входит в секцию. Если есть элемент уже, то просто входит в секцию, инкрементируя счётчик. На деструкторе выходит из секции, декрементирует счётчик. Если счётчик == 0, удаляет секцию.
Как это охуенно используется? А вот так:
[code]
void WINAPI yobaWriter(PVOID args) {
//...
{
auto s = Section("VAJNYY_FAYL");
//...
}
//...
}
void WINAPI yobaReader(PVOID args) {
//...
{
auto s = Section("VAJNII_FAIL");
//...
}
//...
}
[/code]
Можно ещё сделать какой-нибудь макрос
#define CrSection(x) auto _currentCriticalSection = Section(x);
Тогда можно использовать как
{
CrSection("VAJNII_FAYL");
}
Элегантное решение для синхронизации критическими секциями.
Есть класс КритикалСекшн. У него есть коллекция туплов примерно таких<std::string, size_t count, HANDLE>. Конструктор класса принимает строку. Если нет в коллекции записи с такой строкой, создаёт критическую секцию соответсвтующую, добавляет в коллекцию, на сайз_т делает 1, входит в секцию. Если есть элемент уже, то просто входит в секцию, инкрементируя счётчик. На деструкторе выходит из секции, декрементирует счётчик. Если счётчик == 0, удаляет секцию.
Как это охуенно используется? А вот так:
[code]
void WINAPI yobaWriter(PVOID args) {
//...
{
auto s = Section("VAJNYY_FAYL");
//...
}
//...
}
void WINAPI yobaReader(PVOID args) {
//...
{
auto s = Section("VAJNII_FAIL");
//...
}
//...
}
[/code]
Можно ещё сделать какой-нибудь макрос
#define CrSection(x) auto _currentCriticalSection = Section(x);
Тогда можно использовать как
{
CrSection("VAJNII_FAYL");
}
Можно вместо строк использовать какие-нибудь указатели, и будет аналог синхронайзд блоков в Джаве.
1. Работа с туплами медленная.
2. Сравнение строк очень медленное.
3. Кому принадлежит коллекция? Классу как статическая? А как же расширяемость? Если понадобится две коллекции для разных задач, придется все перепиливать. очень. очень плохая идея.
4. Доступ к чему ты синхронизируешь? У тебя я вижу только регистрацию количества обработчиков файла, никакой синхронизации нет. Ни обработчик, ни код снаружи твоего класса вообще не узнают, был увеличен счетчик, или создана новая секция. Так что либо я тебя неправильно понял, либо ты сделал какой-то ебаный регистратор, который непонятно зачем считает обработчики и больше ничего не делает.
5. В любом случае синхронизация не обеспечивается. Без атомарных операций, очевидно, методы могут вызваться одновременно, увеличить счетчик один раз вместо двух и вообще хуй знает что натворить.
6. Раз уж ты вынужден использовать примитивы синхронизации, вместо вновь придуманного странного медленного велосипеда не лучше ли использовать возможности языка? Критические секции легко моделируются мьютексами, более того, в большинстве случаев они не нужны, потому что можно разбить задачу на независимые и использовать async/future.
7. Макросы.
8. WinAPI.
???????
FAIL
Спрашивал же нужно ли перед изучением крестов асм подучить. http://arhivach.org/thread/78455/#465309 И что делать? Таненбаума читать долго, а те 2 точно помогут? Они вроде больше по асм чем архитектуре ЭВМ. Но освоив одну из них смогу дальше учить С++? Это же они? http://arch.cs.msu.su/semestr2/%CF%E8%EB%FC%F9%E8%EA%EE%E2%20%C2.%CD.%20%CF%F0%EE%E3%F0%E0%EC%EC%E8%F0%EE%E2%E0%ED%E8%E5%20%ED%E0%20%FF%E7%FB%EA%E5%20%E0%F1%F1%E5%EC%E1%EB%E5%F0%E0%20IBM%20PC,%C4%E8%E0%EB%EE%E3-%CC%C8%D4%C8,1999.pdf ftp://92.200-224-87.telenet.ru/%D3%F7%E8%EC%F1%FF/Assembler/%DE%F0%EE%E2.%20%C0%F1%F1%E5%EC%E1%EB%E5%F0.pdf
> 1. Работа с туплами медленная.
Вместо него можно класс с тремя полями, всё равно.
> 2. Сравнение строк очень медленное.
Я об этом писал. Можно как-нибудь хешировать, а можно вместо строк делать с указателями, чтобы как в джавке синхронайзд(и тут объект синхронизации).
> 3. Кому принадлежит коллекция? Классу как статическая? А как же расширяемость? Если понадобится две коллекции для разных задач, придется все перепиливать. очень. очень плохая идея.
Зачем разные? Все секции в одной коллекции.
> 4. Доступ к чему ты синхронизируешь? У тебя я вижу только регистрацию количества обработчиков файла, никакой синхронизации нет. Ни обработчик, ни код снаружи твоего класса вообще не узнают, был увеличен счетчик, или создана новая секция. Так что либо я тебя неправильно понял, либо ты сделал какой-то ебаный регистратор, который непонятно зачем считает обработчики и больше ничего не делает.
На конструкторе есть же EnterCriticalSection(), на деструкторе - LeaveCriticalSection()
> 5. В любом случае синхронизация не обеспечивается. Без атомарных операций, очевидно, методы могут вызваться одновременно, увеличить счетчик один раз вместо двух и вообще хуй знает что натворить.
Перед увеличением будет EnterCriticalSection(), а LeaveCriticalSection() после декремента. Таким образом, нельзя будет Поменять значение, не находясь в критической секции, а в ней только 1 поток. Всё норм обеспечивается.
> Критические секции легко моделируются мьютексами,
Ну да, в POSIXе как раз мутексы вместо секций. Но выразительнее намного будет
[code]
{
Section("COM1");
//....
}
[/code]
[code]
EnterCriticalSection(p);
//...
LeaveCriticalSection(p);
[/code]
С виду разница не большая. Однако будет очень неприятно передавать указатель на секцию в поток через void* и всё такое. А потом ещё как-то отслеживать неиспользуемые секции и удалять их. То же самое с pthread_mutex_lock/unlock, а ведь для них реализация такая же.
> 8. WinAPI.
И в том и суть, что решение оборачивает WinAPI.
> 1. Работа с туплами медленная.
Вместо него можно класс с тремя полями, всё равно.
> 2. Сравнение строк очень медленное.
Я об этом писал. Можно как-нибудь хешировать, а можно вместо строк делать с указателями, чтобы как в джавке синхронайзд(и тут объект синхронизации).
> 3. Кому принадлежит коллекция? Классу как статическая? А как же расширяемость? Если понадобится две коллекции для разных задач, придется все перепиливать. очень. очень плохая идея.
Зачем разные? Все секции в одной коллекции.
> 4. Доступ к чему ты синхронизируешь? У тебя я вижу только регистрацию количества обработчиков файла, никакой синхронизации нет. Ни обработчик, ни код снаружи твоего класса вообще не узнают, был увеличен счетчик, или создана новая секция. Так что либо я тебя неправильно понял, либо ты сделал какой-то ебаный регистратор, который непонятно зачем считает обработчики и больше ничего не делает.
На конструкторе есть же EnterCriticalSection(), на деструкторе - LeaveCriticalSection()
> 5. В любом случае синхронизация не обеспечивается. Без атомарных операций, очевидно, методы могут вызваться одновременно, увеличить счетчик один раз вместо двух и вообще хуй знает что натворить.
Перед увеличением будет EnterCriticalSection(), а LeaveCriticalSection() после декремента. Таким образом, нельзя будет Поменять значение, не находясь в критической секции, а в ней только 1 поток. Всё норм обеспечивается.
> Критические секции легко моделируются мьютексами,
Ну да, в POSIXе как раз мутексы вместо секций. Но выразительнее намного будет
[code]
{
Section("COM1");
//....
}
[/code]
[code]
EnterCriticalSection(p);
//...
LeaveCriticalSection(p);
[/code]
С виду разница не большая. Однако будет очень неприятно передавать указатель на секцию в поток через void* и всё такое. А потом ещё как-то отслеживать неиспользуемые секции и удалять их. То же самое с pthread_mutex_lock/unlock, а ведь для них реализация такая же.
> 8. WinAPI.
И в том и суть, что решение оборачивает WinAPI.
Если тебе не нужен асм, то читай Пильщикова да, это та книга, пропуская моменты, где рассказывается про команды и само программирование. Юрова в таком случае не надо в основном асм и многабукаф. Еще наверни вот http://arch.cs.msu.su/ это, там курс лекций уже чисто по архитектуре, который читают у нас параллельно с практикумом по Пильщикову во втором семестре. Вместо Таненбаума можешь взять http://ftp.vtyulb.ru/%D0%9E%D0%BF%D0%B5%D1%80%D0%B0%D1%86%D0%B8%D0%BE%D0%BD%D0%BD%D1%8B%D0%B5%20%D1%81%D0%B8%D1%81%D1%82%D0%B5%D0%BC%D1%8B%20%28%D0%BC%D0%B0%D1%88%D0%B1%D1%83%D0%BA%29.pdf это, там курс по операционным системам, который читают в третьем семестре. По сути тот же Таненбаум, но гораздо более сжатый многие фишки не рассказаны, но для ознакомления самое то. Главы 4 и 6 можешь пропустить, остальное читай.
У него ещё путаница с терминологией.
Критическая секция — это режим выполнения, когда программа становится однопоточной и её приоритет повышают на то время, пока она находится в критической секции (гуглить VxWorks и другие ОСРВ).
lock (obj) {} и «новейшая очень классная идея» — это не критическая секция, а семафоры, причём со способностью впадать во взаимную блокировку, догадайтесь как.
А, ну тогда за работоспособность этого я не могу сказать тебе, но энивей, на мой взгляд, прикручивать какие-то платформозависимые методы это не особо хорошо. Тем более, что POSIX мьютексы сам не перевариваю это говно с одним методом и кучей флагов на все действия - это уровень 80-х, а у нас тут новый стандарт, знаешь ли. Получается очень выразительно, наподобие std::lock_guard <mutex> guard (lock_) пишешь в конструкторе/начале блока, и пока guard в видимости, ты владеешь секцией. Алсо, такой подход с RAII будет exception-safe из коробки, в отличие от. Не получится забыть выйти из секции в деструкторе и вот это все.
По поводу неиспользуемых секций - ну так это опять велосипед жи. Допустим, ты, возможно, будешь использовать функтор-секцию. Тогда ты делаешь фабрику, когда кто-то дергает получение еще не существующей секции, она генерит функтор, отдает std::shared_ptr на него, а себе схороняет std::weak_ptr. Если у нее дергают получение уже существующей, она пытается отдать shared, сконструированный из weak. Когда пользователи сделают свои дела и счетчик shared станет 0, он удалит секцию автоматически. И все это реализовано наиболее быстрыми путями и thread-safe. Попробуй пересесть со своего велосипеда на мотоцикл короче, лол.
Спасибо. Я зря полез в эту тему не изучая новый стандарт по этому поводу. Почитаю сегодня.
Ну не, критические секции тоже являются одним из примитивов синхронизации, наряду с семафорами. В некоторых языках это базовая вещь вместо мьютекса, ты как-то описываешь, что в участок кода может войти только один поток одновременно. Но, понятное дело, критические секции и мьютексы реализуются элементарно друг через друга, поэтому по факту это одни и те же способы что-либо сделать, и проблемы у них одинаковые.
Спасибо. Оно.
Как перейти с знания языка уровня laba7 на уровень нормального разработчика?
Читай книжки.
Я не хочу писать очередной блокнот или клиент-сервер ибо это тупо, я хочу что-нибудь пооригинальнее (но не знаю что, и даже не могу придумать). Поэтому нихуя не пишу, кроме простеньких, нужных по учебе, программок. Как быть, что написать?
http://www.ideamachine.io/
http://theinternetwishlist.com/
закрепите это уже где-нибудь в шапке
Вот его и пиши. /discussion
добавляешь кастомный QGraphicsItem, в котором рисуешь прозрачный прямоугольник.
В Алёна-треде ни за что.
Ты сейчас про дружественные методы? Так что бы они были видны всем твоим друзьям
Методы снаружи - читаемый интерфейс. Методы внутри - читаемей реализация (что спорно). Интерфейс класса читают намного чаще чем релизацию.
Если ты про друзей, то такое часто бывает при определении операторов над классами. Например, ты хочешь сделать TvoyaMamka & opearator+ (const TvoyaMamka &), где первое слагаемое передается неявно как this. Если у тебя определен еще implicit конструктор, например, из int, то будут проблемы, когда ты пытаешься складывать мамок с числами, потому что неявно передаваемый параметр никогда не приводится автоматически. И тогда ты выносишь operator+ за пределы класса, он теперь принимает параметрами обеих мамок и все работает.
Еще часто обработку объектов выносят за пределы самих классов, потому что метод-член видит приватную реализацию, а внешняя функция видит только интерфейс, и инкапсуляция повышается. Другое дело, что обычно для таких целей можно создать класс-обработчик, в котором будут эти методы.
Ну так ты определяешь класс в заголовочном файле обычно. Если у него большие методы, то это неудобно читать становится, а так можно вынести каждый метод хоть в отдельный .cpp и все будет заебись. Но главное даже не в этом, а в том, что если ты меняешь реализацию метода без изменения интерфейса (те же параметры, то же возвращаемое значение), то тебе придется перекомпилировать только один файл. А если реализация в заголовочном файле, то перекомпилируются все .cpp, которые его используют. В больших проектах это настолько существенно, что делают дополнительные сущности, чтобы клиент как можно меньше знал о реализации, в.т.ч. и данных, называется pimpl. Делают маленький хедер, в котором объявлен прокси-класс. В нем указатель на настоящий объект и больше нихуя. Пока ты не используешь объект, тебе не нужно ничего знать о реализации, размере и всем таком, если ты хранишь в другом объекте не его самого, а указатель. Это позволяет избежать порчи половины проекты, когда ты добавляешь член в один хедер, который оказывается подключен к куче других.
Спасибо, ты крутой.
Собственно, почему спрашиваю. Поставлена задача: есть N файлов, общим размером ~100мб. В файлах отсортированные номера. Нужно создать один файл со всеми номерами. Разумеется, тоже отсортированный. При этом, нужно уложиться в 50мб оперативки.
Я планировал решить это следующим образом: так как номера в файлах отсортированы, просто выдергивать из каждого файла по одному номеру и образовавшуюся коллекцию сравнивать между собой. Ну и выдернутые номера удалять, например. Это хороший подход или я не прав?
Файлы не пихаются целиком в память. Читай по одному, сравнивай, записывай. Удалять их из файлов не обязательно, файл будет читаться дальше сам по себе.
>Читай по одному
Держать открытыми сразу все файлы - не очень?
Каждый раз открывать/закрывать?
Тут несколько вариантов:
1) Допустим, у тебя оперативной памяти было бы не 50мб, а 1 мб. Тогда можно было бы, например, считывать из одного файла порцию данных в буфер и из другого файла порцию данных (в жизни из файла не читаются побитово, а читаются целыми блоками по X килобайт). Далее сливать эти два буфера и записывать их в третий новый файл (данные идут на диск). В итоге у тебя получится отсортированный файл, содержащий данные двух исходных файлов. Повторять так N - 1 раз, в конце получишь один отсортированный файл.
2) Т.к. у тебя 50 метров, а все файлы - 100 метров, то выгоднее сразу все считать 50 метров из файлов в память, отсортировать любым нормальным алгоритмом сортировки, записать в файл и не париться (т.к. работа с диском очень-очень медленная, а работа с памятью невероятно быстрая). Потом повторить тоже самое для оставшейся части файлов (остальные 50 метров). А потом два файла слить через алгоритм из первого пункта.
А вот в первом случае на N-(N / 2) итерациях разве не будет такого, что в буфер придется записать данных большем, чем на 50мб?
Черт. Уже час не могу написать - двачестан возвращает Gateway timeout
>Весь объем файла пихается в оперативную память или нет?
Пихается буфер, зависящий от libc и системы. По-моему в районе 64 кб. Поэтому даже побайтовое чтение не вызывает проблем с производительностью, но и файлы, конечно, целиком не грузятся.
>При этом, нужно уложиться в 50мб оперативки.
Домашка? Вообще так делается merge sort, именно как ты описал.
В первом случае ты считываешь в память, считай, 1 число из одного файла и 1 число из другого файла. Выбираешь наименьшее из чисел, записываешь в выходной файл. Считываешь из соответствующего файла еще одно число. В итоге в памяти у тебя всегда не больше 2х чисел. А файл целиком в память можно не считывать. Вроде так.
Обращайся. Второй предложенный способ, имхо, круче - память нужно использовать по полной, т.к. это очень быстро.
В памяти будет размер соответствующих буферов чтения. Поэтому лучше не выебываться и доверить буферизацию ("использование памяти по полной") системе.
Лол. Что-то от тебя зеленью запахло, но отвечу. Читать числа по одному, файлы закрывать не нужно.
Пардон. Я на полном серьезе задаю эти глупые вопросы. Конечно стараюсь читать самостоятельно, но иногда проще спросить.
Хмм. А почему, если сделать вот так:
\tint k = 12345678;
\tofstream out ("out.txt", ios::out);
\tout << k << endl;
\tout.close();
то размер файла будет 10 байт?
Черт. Табы вылезли.
То есть, в винде всегда железно два байта? Вне зависимости от компилятора, библиотек и так далее?
Хорошо. Остановимся на этом. Не буду злоупотреблять твоей помощью. Просто почитаю об этом где-нибудь на досуге.
Большое спасибо.
Это не регламентировано стандартом жи. Библиотека предоставляет тебе некоторую абстракцию файла, который может находиться где угодно. Например, ты открываешь последовательный порт как файл, или удаленный файл на чужой пекарне. В *nix вообще все считается файлами даже небо, даже Аллах. Понятно, что последовательный порт или поток ввода который ВНЕЗАПНО тоже файл нельзя схоронить в оперативную память, потому что неизвестно, что в них будет потом. Но даже если ты оперируешь с "хорошим" файлом с диска, он банально не может влезть в память. Пораскинь мозгами, анон, когда ты открываешь йоба-фильм в .mkv на 30 гигабайт, он целиком не влезает в твою память, но видеоплеер, несомненно, открывает его как файл. А разгадка одна - интерфейс fstream ничего не говорит о том, где находится файл. Он передает строку с именем операционной системе, та достает нечто, что в ее понимании отвечает твоему запросу, и тебе предоставляется к этой сущности доступ. Она физически может быть где угодно, и ты не можешь "заметить" этого, потому что время доступа к файлу тоже не регламентировано. Более того, получится ли открыть файл - тоже не регламентировано, эта ответственность возлагается на ОС, как и способ хранения кусков открытого файла. Скорее всего, нормальная ОС будет загружать файл по кускам и кэшировать. Но теоретически она может попытаться загрузить весь файл в память, памяти не хватит, и конструктор fstream кинет исключение емнип. И такое поведение абсолютно нормально и не выходит за рамки стандарта. такие дела.
Логично. Спасибо.
Метапрограммирование жи.
Поиск максимума из n чисел во время компиляции:
[code lang="cpp"]
template <int head, int ... tail>
struct Max
{
\tconst static int value = (head > Max <tail ...>::value) ? head : Max <tail ...>::value;
};
template <int ... tail>
struct Max
{
\tconst static int value = std::INT_MIN;
};
[/code]
>Поиск максимума из n чисел во время компиляции:
поясни что тут происходит. И как делать что-то похожее.
мимо
>emplace-методы, это и есть функции с переменным числом параметров
Не путай, тебе же станет известно количество параметров еще при компиляции, поэтому переменное количество параметров, значит, делать variadic function не требуется. Например, у тебя есть класс ChlenSemyi, в котором unique_ptr <T> chlen_, где T может быть TvoyaMamka, у которой конструктор принимает 10 параметров-кусков мяса, либо TvoyBatya, который дохуя спортсмен и принимает только один параметр-салат. Тебе нужно инициализировать этот указатель в конструкторе класса ChlenSemyi. И ты можешь создать один variadic template конструктор, который принимает любое количество любых параметров и пытается пихнуть их в конструктор T. Без них тебе бы пришлось описывать для каждого набора параметров отдельный конструктор.
>каррирование проще делать лямбда-функциями
Не всегда. До C++14 нельзя было переименовывать параметры и захватывать члены класса как переменные из зоны видимости, например, а вариадики подбавляют гибкости.
>и нахуя это нужно?
Потому что это позволяет перенести часть вычислений на этап компиляции, потом тормозить будет меньше я могу, иди на хуй.
Хвостовая рекурсия же. Он на каждом этапе сравнивает первый параметр и уже вычисленное value в структуре, где параметров на один меньше. Когда остается ноль параметров, он вернет наименьший возможный int. Да, я знаю, что это немного костыльно, просто первое, что пришло в голову. Вообще, гугли метапрограммирование или Александреску из шапки читай.
>значит, делать variadic function не требуется
При чем тут вообще variadic function, если изначально речь идет о шаблонах?
>До C++14 нельзя было переименовывать параметры и захватывать члены класса как переменные из зоны видимости
если речь идет о [&,=], то это прекрасно работало и в 11.
Скинь какой-нибудь пример каррирования шаблонами
>При чем тут вообще variadic function
>emplace-методы, это и есть функции с переменным числом параметров
Ты походу не отличаешь template <typename ... Args> func () от func (TvoyaMamka arg1, ...).
>если речь идет о [&,=], то это прекрасно работало и в 11
Нет, речь о [var = expression] {}.
>Скинь какой-нибудь пример каррирования шаблонами
[code lang="cpp"]
template <typename Function, typename ... OldArgs>
class Bind
{
\tconst Function function_;
\tconst std::tuple <OldArgs ...> old_args_;
\t
public:
\tBind (Function input_function, std::tuple <OldArgs ...> args) :
\t\tfunction_ {input_function},
\t\told_args_ {args}
\t{}
\t
\ttemplate <typename NewArg>
\tauto operator() (NewArg arg)
\t{
\t\treturn curryItMotherfucker (arg, 0);
\t}
\t
\ttemplate <typename Arg>
\tstd::result_of_t <Function (OldArgs ..., Arg)> curryItMotherfucker (const Arg & arg, int) const
\t{
\t\treturn function_ (args ..., arg);
\t}
\t
\ttemplate <typename Arg>
\tauto curryItMotherfucker (const Arg & arg, ...) const
\t{
\t\treturn Bind <Function, Args ..., Arg> { function_, std::tuple_cat (args, std::tuple <Arg> (arg))};
\t}
};
[/code]
>При чем тут вообще variadic function
>emplace-методы, это и есть функции с переменным числом параметров
Ты походу не отличаешь template <typename ... Args> func () от func (TvoyaMamka arg1, ...).
>если речь идет о [&,=], то это прекрасно работало и в 11
Нет, речь о [var = expression] {}.
>Скинь какой-нибудь пример каррирования шаблонами
[code lang="cpp"]
template <typename Function, typename ... OldArgs>
class Bind
{
\tconst Function function_;
\tconst std::tuple <OldArgs ...> old_args_;
\t
public:
\tBind (Function input_function, std::tuple <OldArgs ...> args) :
\t\tfunction_ {input_function},
\t\told_args_ {args}
\t{}
\t
\ttemplate <typename NewArg>
\tauto operator() (NewArg arg)
\t{
\t\treturn curryItMotherfucker (arg, 0);
\t}
\t
\ttemplate <typename Arg>
\tstd::result_of_t <Function (OldArgs ..., Arg)> curryItMotherfucker (const Arg & arg, int) const
\t{
\t\treturn function_ (args ..., arg);
\t}
\t
\ttemplate <typename Arg>
\tauto curryItMotherfucker (const Arg & arg, ...) const
\t{
\t\treturn Bind <Function, Args ..., Arg> { function_, std::tuple_cat (args, std::tuple <Arg> (arg))};
\t}
};
[/code]
Учил месяца 3, потом поработал 2 месяца, не фрилансил.
>Ты походу не отличаешь
я писал
>где можно красиво использовать variadic templates, кроме функций с переменным числом параметров?
Если ты знаешь еще какой-то способ, использования variadic templates для реализации переменного кол-ва пераметров кроме emplace-методов, то напиши.
Даже если код напрямую копирую с книги - такая же ошибка.
Как я понял что-то с std_lib_facilities.h не так?
Пока двач висел попробовал ручной метод на 2 скрине, опять странные ошибки.
Чтобы запускать примеры эта библиотека не обязательны. Всё как написано в приложении Г делал?
В оперативной памяти есть специальный стек, когда ты вызываешь функцию, в него помещаются передаваемые ей параметры, а функция при обращении к параметрам считывает их из этого стека. Речь идет о том, кто должен удалять эти данные из стека при выходе из функции: сама функция или вызывающая программа.
Нечто ассемблерное. Выбрось из головы.
Пока писал второй вопрос понял ответ. Спасибо. %%На всяки случай уточню. В ассемблере это делается вручную с помощью push и pop?%
Это называется "соглашение о вызове" и в разных языках и системах оно разное. https://ru.wikipedia.org/wiki/%D0%A1%D0%BE%D0%B3%D0%BB%D0%B0%D1%88%D0%B5%D0%BD%D0%B8%D0%B5_%D0%BE_%D0%B2%D1%8B%D0%B7%D0%BE%D0%B2%D0%B5
Делается это не с помощью push/pop, а спомощью манипуляций с ebp и esp. См. http://stackoverflow.com/questions/15020621/what-is-between-esp-and-ebp
А, это был ответ на вопрос, а не вопрос, лол.
Прости, но я не могу в английский. Можешь пояснить что он тут имел ввиду?
>all local variables and function parameters are a known constant offset from this register for the duration of the function call.
>At the start of the function, ESP is decremented by the appropriate value.
SP указывает на вершину стека и с помощью его можно ложить/брать верхний элимент, а для чего BP?
И в википедии писалось что когда Си ложит переменную меньше 4 байт в стек, то она расширяться до 4 байт. Имеется виде переменная из объявления функции, а не локальная? А если я буду передавать как параметр массив char, то его размер в 4 раза увеличивается? В С++ так же?
Ты заебал, я тебе аж джва примера привел. Максимум чисел на этапе компиляции для адептов метапрограммирования, каррирование без костылей с обертками вокруг лямбды как более практическая вещь.
>all local variables and function parameters are a known constant offset from this register for the duration of the function call.
Когда ты пишешь внутри функции int i; int j; int k компилятор превращает это в [ebp - 4], [ebp - 8], [ebp - 12]. То есть переменные превращаются в смещение относительно регистра ebp.
>At the start of the function, ESP is decremented by the appropriate value.
В начале функции на стеке выделяется память путем вычитания из ESP. Тогда в промеждутке между EBP-ESP находятся твои локальные переменные. Далее push/pop модифицируют ESP, а вот EBP используется для адресации локальных переменных.
>А если я буду передавать как параметр массив char, то его размер в 4 раза увеличивается?
Нет. Массивы обычно передаются по ссылке, но если даже передашь по значению, то размер округлится до кратного 4-х.
Да. Если посмотришь книжку Пильщикова, которая была выше в треде, там наглядно это показано. Идиома такая, что один из регистров (BP для 8086 архитектуры, EBP для 32bit, RBP для 64bit) схороняется в стек, дальше в него записывается вместо старого значения адрес текущей верхушки стека, и все локальные переменные отсчитываются как BP - смещение, а все параметры (и адрес возврата) как BP + смещение.
Всё. Спасибо. Теперь точно понял.
На всякий случай уточню. Если в функцию передавать 100 параметров типа char, а не 1 массив из 100 элементов, то тогда каждая переменная будет занимать 4 байта?
Это емнип зависит от архитектуры. Грубо говоря, ты не должен делать предположений об этом, стандарт не регламентирует. На некоторых архитектурах выравнивание строго обязательно, на других его можно вырубить, но тогда увеличивается время доступа. Изнутри крестов ты это не сможешь контролировать, по крайней мере платформонезависимо.
Не забивай себе голову этим. Байты считать - себя не уважать.
Массивы вообще передаются по ссылке, а сколько будет занимать переменная типа char зависит от архитектуры и компилятора и в с++ тебя это волновать не должно.
>книжку Пильщикова
Она слишком сложная. Не осилил и 10 страниц. Если осилю лекции что выше в треде рядом с этой книгой, то пойму что в ней написано? Если нет, то реквестирую что попроще Пильщикова.
Для начала почитай шапку.
>Пильщикова
>сложная
Эээ, шта? Она же очень поверхностная, я помню, как мне на первом курсе вечно не хватало детализации из нее и приходилось гуглить, лол. Попробуй тогда навернуть лекций по архитектуре для начала, там выше я кидал ссылку на ргхост.
1. BACKGROUND
http://en.wikipedia.org/wiki/Adobe_Flash_Player
Congrats! You are reading about the most beautiful Flash bug for the last four
years since CVE-2010-2161.
2. DESCRIPTION
The use-after-free vulnerability exists inside the built-in ByteArray class
http://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/utils/ByteArray.html
Let's create a simple ByteArray object:
var ba:ByteArray = new ByteArray();
ba.length = 8;
ba[1] = 1;
Now we can access ba[] items and write numeric byte values into ba[].
Also we are allowed to write objects into ByteArray. For example:
var obj = new MyClass();
ba[0] = obj;
AS3 will try to implicitly convert the MyClass object into numeric value by
calling the MyClass.valueOf() method. This method can be easily redefined
within the user's code:
class MyClass
{
prototype.valueOf = function()
{
ba.length = 88; // reallocate ba[] storage
return 0; // return byte for ba[offset]
}
}
Let's see how that implicit conversion occurs inside the native code:
push esi
mov eax, [esp+8] // the offset value from "ba[offset] = obj"
push eax
add ecx, 0x18 // ecx = this = "ba" object pointer
call ByteArray.getStorage() // gets ba[offset] storage pointer and
mov esi, eax // saves it in esi
mov ecx, [esp+0xC] // "obj" pointer
push ecx
call AvmCore.toInteger() // call MyClass.valueOf()
add esp,4
mov [esi], al // writes returned byte into array
pop esi
ret 8
On high-level language this will look like:
void ByteArray.setObjInternal(int offset, obj)
{
byte dest = this.getStorage(offset);
dest = toInteger(obj);
}
So the array storage pointer is saved in local variable, then AS3 valueOf() is
invoked from the native code and returned byte is written into destination
pointer at the end. If valueOf() changes the length of byte array (see above)
and reallocates its internal storage, then local destination pointer becomes
obsolete and further usage of that pointer can lead to UaF memory corruption.
Using this vulnerability, it's very easy to control what byte will be written
and at which offset this corruption will occur.
3. AFFECTED SOFTWARE
Adobe Flash Player 9 and higher
...
Стало интересно пусть они могут записать в освобожденную область памяти, но откуда они знают что эта память уже снова выделена (причем это должно произойти после освобождения но до записи значения) и как она используется?
1. BACKGROUND
http://en.wikipedia.org/wiki/Adobe_Flash_Player
Congrats! You are reading about the most beautiful Flash bug for the last four
years since CVE-2010-2161.
2. DESCRIPTION
The use-after-free vulnerability exists inside the built-in ByteArray class
http://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/utils/ByteArray.html
Let's create a simple ByteArray object:
var ba:ByteArray = new ByteArray();
ba.length = 8;
ba[1] = 1;
Now we can access ba[] items and write numeric byte values into ba[].
Also we are allowed to write objects into ByteArray. For example:
var obj = new MyClass();
ba[0] = obj;
AS3 will try to implicitly convert the MyClass object into numeric value by
calling the MyClass.valueOf() method. This method can be easily redefined
within the user's code:
class MyClass
{
prototype.valueOf = function()
{
ba.length = 88; // reallocate ba[] storage
return 0; // return byte for ba[offset]
}
}
Let's see how that implicit conversion occurs inside the native code:
push esi
mov eax, [esp+8] // the offset value from "ba[offset] = obj"
push eax
add ecx, 0x18 // ecx = this = "ba" object pointer
call ByteArray.getStorage() // gets ba[offset] storage pointer and
mov esi, eax // saves it in esi
mov ecx, [esp+0xC] // "obj" pointer
push ecx
call AvmCore.toInteger() // call MyClass.valueOf()
add esp,4
mov [esi], al // writes returned byte into array
pop esi
ret 8
On high-level language this will look like:
void ByteArray.setObjInternal(int offset, obj)
{
byte dest = this.getStorage(offset);
dest = toInteger(obj);
}
So the array storage pointer is saved in local variable, then AS3 valueOf() is
invoked from the native code and returned byte is written into destination
pointer at the end. If valueOf() changes the length of byte array (see above)
and reallocates its internal storage, then local destination pointer becomes
obsolete and further usage of that pointer can lead to UaF memory corruption.
Using this vulnerability, it's very easy to control what byte will be written
and at which offset this corruption will occur.
3. AFFECTED SOFTWARE
Adobe Flash Player 9 and higher
...
Стало интересно пусть они могут записать в освобожденную область памяти, но откуда они знают что эта память уже снова выделена (причем это должно произойти после освобождения но до записи значения) и как она используется?
Ну это классическое переполнение жи. Обычно тактика такая - засрать всю доступную тебе для записи память пустыми командами, а в конце цепочки поставить RET туда, куда тебе надо. После этого с нехилой вероятностью управление попадет на одну из этих команд и уплывает по ним до твоего RETа.
Но для этого надо, чтобы
А) эту память не перезаписали перед использованием
Б) чтобы она была в исполняемом сегменте.
Не?
не очень понимаю в байтоебстве и асме, не ругайся
Ну вообще да, и энивей сейчас делают всякие защиты запрет исполнения из сегмента данных, автоматическую проверку границ массива с генерацией исключения при выходе, или вообще запускают все недоверенное в песочницах. Переполнение это классика взлома как бы. Но по факту иногда пусть и с изъебствами это работает. Там дохуя разновидностей каждый день придумывают, их быстро патчат, но потом придумывают снова, ну ты понел. Например, лет десять назад нашли фишку с переполнением кучи куча и стек обычно в одном сегменте делались и росли навстречу друг другу, было довольно популярно ее юзать. Но вообще, если тебе это интересно, то ты должен серьезно обмазаться байтоебством. Уровень семестрового асма точно будет необходим. Если хочешь, могу кинуть видео с лекций, которые нам в лабе читали, там одна или две как раз про это, довольно популярно разжевывалось вроде.
Та не, я другой анон вообще. Асм очень поверхностно понимаю и мне норм.
Это из архива hacking team readme, у них сэмплы есть которые хорошо работают (под винду и макось). Можешь их исходники посмотреть если разбираешься
http://t.co/nfqck54YhT
Не забудь тут рассказать :3
https://www.youtube.com/playlist?list=PL2AE27C02108EDDF4
Вот тут с 7 по 10 про программные уязвимости и вот это все.
Спасибо. Завтра гляну и отпишусь.
> Подробно работа отладчика студенты факультета вычислительной математики и кибернетики МГУ изу-
чают в курсе третьего семестра "Системное программное обеспечение".
Что это за курс? Он у тебя есть? Можешь показать?
И так много тредов уже. Ещё 1 не навредит.
Почему тяфкает на последнюю фигурную скобку?
Потому_что_блока_do{}_не_бывает
Спасибо тебе.
Поле if тоже нужны скобки, кстати.
>Там же рядом учебник написан, вроде оттуда всё скатал, а не работает...
Другой компилятор или другая версия. В MS не работал, но возможно там надо .h и для стандартных библиотек. Ещё попробуй на первом скрине удалить из скаченого файла #include <hash_map>
Няш, ну я бы мог, конечно, но с асмом не такая движуха, как с крестами же. Вангую, что тред будет мертворожденным просто, иногда кто-то будет заходить из-за шапки и все. Да и я, если честно, в асме шарю только на уровне, чтобы понимать, что вообще происходит, и иногда ломать что-то. Асм-погроммистом меня никак нельзя назвать.
>>510787 >>510805
У нас изменилась программа, учебник же старый. Сейчас в третьем семестре вместо этого операционные системы , а СПО читают только на кафедре СП емнип. Про отладчик было примерно поллекции, я выше давал ссылку на книжку Машечкина по операционным системам, она в точности по лекциям, так что можешь обмазаться. Там про трассировку, точки останова и вот это все.
>>510799
Не, пока еще студент. Ну, во-первых, пошарь по сайтам погроммистских кафедр, это cs.msu.su с префиксами al. , sp. , asvk. Еще есть http://esyr.nizm.ru/ и http://tka4.org/materials/, там много материалов.
мимооп
замени hash_map на unordered_map, заинклудь <unordered_map>, измени подсистему в настройках проекта на /SUBSYSTEM:CONSOLE (Project->Properties->Linker->System->SubSystem)
По поводу обработчиков сигналов - это довольно просто, лол. В nix процессы могут посылать друг другу сигналы это просто числа, которые обозначаются как константы через #define, например, SIGKILL, эти сигналы передаются и обрабатываются отдельно от потоков ввода-вывода, файлов и других инструментов взаимодействия. Когда процесс получает сигнал например, нажатие Ctrl+C в консоли посылает SIGINT работающей программе, ищется обработчик сигнала с таким номером и вызывается. Обработчик это просто функция вида void func (int), в параметр ей суется номер сигнала. Процесс имеет изначально обработчики по умолчанию которые при получении сигнала вырубают процесс нахуй, но если тебе не нравится, то ты можешь переопределить обработчик на кастомный. Для этого есть функция signal, она выглядит как void (signal(int sig, void (*func)(int)))(int), то бишь принимает номер сигнала и указатель на новый обработчик, заменяет его, и возвращает указатель на старый обработчик. Вот и все. Но это такие дебри Pure C, лол, в крестах обходятся без такой хуйни обычно.
Еще один долбоеб со спойлерами вместо скобок.
Кормен, Лейзерсон - Алгоритмы: Построение и анализ.
Бентли - Жемчужины программирования.
Уоррен мл. - Алгоритмические трюки для программистов.
>А то вот все пиздят, мол главное чтоб знал АЛГОРИТМЫ.
Вообщем-то правильно пиздят, но не совсем. АЛГОРИТМЫ - это не знание, это навык\способность\умение - приходит с опытом. Чем больше ты реализуешь алгоритмов, тем больше опыта ты набираешься. Так что гоу в сортировку. Научисть в блок-схему алгоритма. Пойми рекурсию. Потом всякие стеки очереди реализуй. Потом деревья, кольцевые буферы и всякие там скип-листы. Потом разберись с потокбезопасностью - критические секции, мутексы, семафоры, спин-локи и пр. Потом всякие потокобезопасные lock-free, wait-free алгоритмы на interlocked-операциях ебашь, узнай что-такое ordering, cache-line и false sharing. Как-то так.
>Выглядит это все так, как будто нахуй не нужно.
Только это и нужно. ЯП - это вторичное, тебе к тому времени уже должно быть похуй на каком языке\парадигме и под какую ОС что писать.
void hello_anon(int&& i)
{
cout<<"i = "<<i<<endl;
i=100500;
}
int main()
{
hello_anon(10); //ok
int tmp=20;
//hello_anon(tmp); //error lvalue to rvalue
hello_anon((int&&)(tmp)); //ok
cout<<"tmp = "<<tmp<<endl; //tmp=100500
int tmp2=30;
hello_anon((int)(tmp2)); //ok
cout<<"tmp2 = "<<tmp2<<endl; //tmp2=30
return 0;
}
Так вот, в чем вопрос: мне всегда казалось, что приведение типов никак не влияет на передаваемые данные, это просто способ обойти ограничения компилятора, однако tmp и tmp2 ведут себя по разному, получается приведение типов генерит какой-то код?
Передаешь 10 - rvalue передается, печатается, устанавливается в 100500 и исчезает.
Передаешь tmp - компилятор не дает передать и испортить lvalue.
Передаешь (int &&) (tmp) - аналогично std::move ты показываешь, что tmp можно портить как rvalue. Сгенерится ссылка и передастся в функцию, как и в случае 10. Код будет такой же как для 10, ибо приведение указателей не генерит нового кода если нет приведения между наследующими классами, у которых смещения разные.
Передаешь (int)(tmp2) - здесь ты приводишь не указатели, а значения. Поэтому вызовется "конструктор" int на самом деле у int нет конструктора, но упрощенно можно считать, что произойдет то же, что при конструировании нового объекта класса, ведь даже синтаксис тут фактически соответствует: ты пишешь int (tmp2), вот тебе и конструктор. В итоге tmp2 скопируется во временный rvalue int, и уже ссылка на него будет передана в функцию. Этот временный int изменится на 100500, а старый, разумеется, нет. А разгадка одна - приведение не для указателей, а для самих объектов очень даже может генерировать код и не только явное, например, int в double приводится не бесплатно, хранятся они совершенно по-разному.
Бамп.
Вы видите копию треда, сохраненную 4 августа 2015 года.
Скачать тред: только с превью, с превью и прикрепленными файлами.
Второй вариант может долго скачиваться. Файлы будут только в живых или недавно утонувших тредах. Подробнее
Если вам полезен архив М.Двача, пожертвуйте на оплату сервера.