我有一个示例代码块:
#include <iostream>
#include <iomanip>
#include <string>
using namespace std;
int main(){
string blank = " ";
cout << "Hello" << blank << "47";
}我的原始代码中有很多这种类型的cout。我希望能够将空白字符串更改为setw(2)函数,而不必在代码中的每个cout上用setw(2)替换空白。那么,是否有办法将cpp函数设置为变量?所以我可以通过输入名称来调用这个函数?例如:
func blank = setw(2);
cout<< "Hello" << blank << "47";发布于 2017-11-12 15:42:44
std::setw(x)的类型是未指定,但您不需要知道它。
您可以只使用auto
auto blank = std::setw(2);正如@StoryTeller所指出的,虽然这应该适用于正常的实现,但并不一定能做到这一点。
一个更安全的选择是使用重载的<<创建一个类
struct blank_t {} blank;
std::ostream &operator<<(std::ostream &s, blank_t)
{
return s << std::setw(2);
}发布于 2017-11-12 15:40:57
std::setw是一个操纵者。其类型未指定,且实现特定。
那么,是否有办法将cpp函数设置为变量?
使用C++11,您可以使用功能对象,特别是std::function。你也有lambda表达式。
我不确定你是否想把它用在你的箱子里。
因此,学习使用您的源代码编辑器。用适当的东西替换blank的每一次发生,即std::setw(2) .这使您的代码更具可读性。优秀的编辑可以轻松地做到这一点。
你可以滥用预处理器
#define blank setw(2)但在您的情况下,这是个坏主意(因为代码仍然不可读)。即使使用auto作为由HolyBlackCat回答,也会使您的代码无法阅读和混淆。
读代码比写代码要频繁得多。保持它的可读性(即使是你自己,在几周内)。
如果您有一个庞大的(百万行)项目,在这种情况下,可以花几分钟编写一些脚本来修改源代码。顺便说一下,使用GNU emacs很容易(因为emacs是一个可编写脚本的编辑器)。
发布于 2017-11-12 17:01:40
另一种解决方案是编写一个小型包装类,其唯一目的是为封装的引用对象提供重载的operator<<。您可以临时处理这个类,这样它就可以与您能够提供给std::ostream的所有内容一起工作。
下面是一个示例:
#include <iostream>
#include <iomanip>
#include <string>
template <class T>
struct Blank {
Blank(T const& t) : t(t) {}
T const& t;
};
// utility function so that you can use type deduction at the call site:
template <class T>
Blank<T> blank(T const& t) {
return Blank<T>(t);
}
template <class T>
std::ostream& operator<<(std::ostream& os, Blank<T> const& blank) {
os << std::setw(2) << blank.t;
return os;
}
int main() {
std::cout << "Hello" << blank("4") << blank(7) << blank(std::string("8")) << '\n';
}这并不完全是您所要求的语法,但它非常接近。
您还必须确保在operator<<中使用封装对象之前没有破坏它(因为这样您就会因为一个悬空引用而具有未定义的行为),但是如果不创建命名的Blank对象,这很容易实现。
https://stackoverflow.com/questions/47250607
复制相似问题