Я согласен, что это не приятный код.Чтобы избежать повторения, проделайте то же самое, что и всегда при программировании: encapsulate - в этом случае инкапсулируйте структуру и придав ей надлежащий конструктор, и напишите тонкую оболочку вокруг boost::lexical_cast<int>(x)
.
Или, если вы хотите избежать переноса SDL_Rect
, напишите функцию инициализатора:
template <typename TString>
int parse_int(TString const& value) { return boost::lexical_cast<int>(value); }
void init_sdl_rect_from_args(
SDL_Rect& rect, std::vector<std::string> const& args, unsigned offset)
{
rect.x = parse_int(args[offset + 0]);
rect.y = parse_int(args[offset + 1]);
rect.w = parse_int(args[offset + 2]);
rect.h = parse_int(args[offset + 3]);
}
А затем:
SDL_Rect middle = RectZeroes;
if (args.size() >= 6)
init_sdl_rect_from_args(middle, args, 3);
SDL_Rect left_edge = RectZeroes;
if (args.size() >= 10)
init_sdl_rect_from_args(left_edge, args, 7);
Еще лучше, сделайте инициализатор return построенная структура.Это делает его еще более удобным для использования (а именно в инициализаторе):
SDL_Rect rect_from_args(std::vector<std::string> const& args, unsigned offset) {
SDL_Rect rect;
rect.x = parse_int(args[offset + 0]);
rect.y = parse_int(args[offset + 1]);
rect.w = parse_int(args[offset + 2]);
rect.h = parse_int(args[offset + 3]);
return rect;
}
SDL_Rect middle = (args.size() >= 6) ? rect_from_args(args, 3) : RectZeroes;
SDL_Rect left_edge = (args.size() >= 10) ? rect_from_args(args, 7) : RectZeroes;