int a{5},b{2},c{9};
double d = (double)a/(double)b + (double)c;
Или я могу использовать static_cast
. В любом случае это многословно, особенно когда формула длинная. Есть ли лучшее решение?Как преобразовать целое число в двойное неявно?
int a{5},b{2},c{9};
double d = (double)a/(double)b + (double)c;
Или я могу использовать static_cast
. В любом случае это многословно, особенно когда формула длинная. Есть ли лучшее решение?Как преобразовать целое число в двойное неявно?
Можно умножать до 1,0:
int a{5},b{2},c{9};
double d = 1.0 * a/b + 1.0 * c;
И когда вы работаете с суммами возможных для использования 0.0:
double d = 0.0 + a - b + c;
Большинство компиляторов сделать оптимизацию и действительно такая операция не проводилась. Выполняется только преобразование типа.
Обратите внимание, что вам нужно отдать только первый член в каждой группе раздельно/умножить. В любом решении, что вам нравится. И простые дополнения/подзаголовки (без каких-либо других множителей/девайсов типа) тоже бросаются. Компиляторы гарантируют отливку. Так что ваш пример:
double d = (double)a/(double)b + (double)c;
Действительно, может быть переписан как один из этого:
double d = (double)a/b + c;
double d = 1.0 * a/b + c;
double d = static_cast<double>(a)/b + c;
всего несколько примеров:
double d = (double)a/b + (double)c/d + e;
double d = 1.0 * a/b + 1.0 * c/d + e;
double d = static_cast<double>(a)/b + static_cast<double>(c)/d + e;
Если что-то сомнительно («большинство компиляторов»), вы не должны этого делать. –
Когда кто-то касался таких тонких деталей, ему нужно: 1. прочитать руководство по компилятору цели или 2. построить тесты производительности на нем или 3. использовать отладчик, чтобы просмотреть сгенерированный код, чтобы его проверить. Я думаю, что старые компиляторы вроде K & R не делают этого, но нынешние разработчики компиляторов хотят быть реальными. – oklas
Переписывание, то, что предназначено для приведения в бессмысленное умножение, является действительно плохим предложением. Если бы я прочитал код, мне пришлось бы остановиться и подумать, проверить историю кода, возможно, удалить ненужное умножение, перекомпилировать, только чтобы узнать, что это должно было быть «static_cast» с самого начала. Не делай этого. Используйте бросок, когда вам нужно конвертировать между типами. – IInspectable
Есть ли лучшее решение?
Да. Экспресс-намерение через функции.
Marvel as the optimiser испускает совершенно эффективный ассемблер. Наслаждайтесь почестями ваших коллег, кто смотрит в изумлении на свой грозно читаемый и поддерживаемый коде:
#include <iostream>
auto a_over_b_plus_c(double a, double b, double c)
{
double d = a/b + c;
return d;
}
int main()
{
int a = 5, b = 2, c = 9;
std::cout << a_over_b_plus_c(a, b, c) << std::endl;
}
Для развлечения, вот решение, основанное на кортежах & лямбды:
#include <iostream>
#include <tuple>
template<class T, class...Args>
auto to(Args&&...args)
{
return std::make_tuple(T(std::forward<Args>(args))...);
}
int main()
{
int a = 5, b = 2, c = 9;
auto calc = [](auto&& vals) {
auto& a = std::get<0>(vals);
auto& b = std::get<1>(vals);
auto& c = std::get<2>(vals);
return a/b + c;
};
auto result = calc(to<double>(a, b, c));
std::cout << result << std::endl;
}
... и что-то, возможно, более читаемым ...
#include <iostream>
#include <tuple>
#include <complex>
template<class T, class F, class...Args>
auto with(F f, Args&&...args)
{
return f(T(std::forward<Args>(args))...);
}
int main()
{
int a = 5, b = 2, c = 9;
auto calc = [](auto&& a, auto&& b, auto&& c) {
return a/b + c;
};
auto result = with<double>(calc, a, b, c);
auto result2 = with<float>(calc, a, b, c);
auto result3 = with<std::complex<double>>(calc, a, b, c);
auto result4 = with<std::complex<float>>(calc, a, b, c);
std::cout << result << std::endl;
std::cout << result2 << std::endl;
std::cout << result3 << std::endl;
}
Спасибо, что ознакомили меня с типом 'auto' return! – Titulum
@ Титулум: 'auto' не является типом. Я не могу подчеркнуть это достаточно. –
@LightnessRacesinOrbit Я написал это по привычке. Я не собирался делать заявление. Если вы считаете, что это глупо и вводит в заблуждение, пожалуйста, отредактируйте ответ. –
Вы протестировали это? Это работает? –
Выберите стиль и будьте последовательны. Двигаться дальше. Если вы сомневаетесь, проверьте список языков ассемблера для всех ваших разных случаев. Выберите наиболее читаемый. –
Приведение к двойному подчеркивает преобразование из int, что хорошо для любого, кто читает код. –