Писать код без какого-либо плана как-то не особо, и я этим всегда грешил.
Написание архитектуры заранее создает общую картину того что ты вообще хочешь написать, обдумать какие-то сложности которые в будущем могут возникнуть, ну и все такое. Как научиться создавать архитектуру, а то я тупой и мне сложно, я обычно просто накатываю что-то в духе (программа состоит из n модулей, они делают вот это. А еще выборку действий надо сделать через массив указателей на функции, нормас будет).
Нажмите, чтобы раскрыть...
Если ты будешь пытаться проанализировать все сложности изначально, то у тебя ничего не выйдет. Оптимизация - это всегда самое последнее в цепочке.
То же самое касается архитектуры. Если ты в одиночку пишешь проект, то не нужно пользоваться инструментами энтерпрайз уровня. Достаточно просто описать примерный функционал, который ты хочешь получить в итоге, постараться максимально его урезать, выкинув остальное в будущие релизы. Соответственно этому функционалу подобрать необходимые инструменты, которые закроют ответы на вопросы типа: где хранить данные? каким будет интерфейс? и тп. Подобрать набор знакомых уже вещей, так как учиться в процессе создания чего-то нового - это затратно (с другой стороны если цель именно в изучении через практику, тогда это имеет смысл, но как я понял здесь речь не об этом). И собственно начать погружаться на более низкие уровни абстракции для каждого юнита участвующего в создании необходимого тебе функционала.
Пока у тебя не будет прототипа, пока у тебя не начнут выполняться тесты, ты вообще не должен думать о каком-либо рефакторинге, профилировании и тем более архитектуре. Все остальное придет только с опытом, теория в данном случае нужна как подкрепление этого опыта. В следующем проекте ты уже сможешь сразу увидеть узкие места и постараться изначально их обойти.
Ну и как вариант, в каждой области существуют примеры успешных проектов, те же готовые шаблоны для вебфреймворков, этого достаточно для начала.