基本上我希望通过工厂方法创建所有子类型(我有一个高大的域层次结构,有200多个类).
因为new
,这不是问题,因为这可以在A(new
私有)中被覆盖.
class A{
protected:
A();
public:
template<class T, typename... ARGUMENTS>
static T* create(ARGUMENTS&&... arguments);
};
class B : public A {
public:
B();
};
void test() {
B b;//compile error wanted here - but as a consequence of inheriting A
}
Run Code Online (Sandbox Code Playgroud)
这里A是"库/框架"类.而B是"用户创建的类".在B上要求typedef或类似可能没问题.
更新:我在A上添加了'create'函数,我打算用它来创建对象.
std::accumulate
并std::reduce
做几乎相同的事情。
的总结std::reduce
说明了一切:
similar to `std::accumulate`, except out of order
Run Code Online (Sandbox Code Playgroud)
在许多情况下,这些函数应该产生相同的最终结果并展示相同的整体功能。很明显,如果您有一些非常重的负载计算等,您可以尝试std::reduce
进行parrelization。IE。从鸟类的角度来看,这里的传统智慧是什么 - 除非明确优化,否则您是否应该始终坚持直率的 std::accumulate ?还是应该默认使用std::reduce
?
如果std::reduce
(选择默认/未选择执行策略)总是至少与std::accumulate
(保存一些指令)一样快,那么我认为只有在订单严格时才应使用累积。
std::call_once
https://en.cppreference.com/w/cpp/thread/call_once
确保以线程安全的方式恰好一次调用了callable。
由于还有其他类似的方法,因此问题是:
什么时候应该使用?它打算解决什么类型的问题?
请提供示例。
After some change of the code-base I came accross this gotcha:
#include <string>
void test(const std::string& s){
}
int main()
{
test(NULL);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
This throws an exception. Changing to 'nullptr' helps nothing (still no error or warning).
I guess my question is, is there a way to detect or find this error at pre-runtime throughout the sourcecode ? perhaps some compiler warning, etc. (using MSVC VS-2017)
I ended up modifying the basic_string template ala. basic_string(int) = delete; …
假设我要制作一个新的演绎指南,以便进行以下操作?
std::string str;
std::basic_string_view sv = str;
Run Code Online (Sandbox Code Playgroud)
Would that be an Ok customization ?
c++ c++-faq language-lawyer deduction-guide class-template-argument-deduction
试图“误用”std::accumulate
算法(为什么它无论如何都在“数字”标题中?;))
template<class Range, class Seperator>
std::string strjoin(Range&& range, Seperator&& seperator) {
if (std::empty(range)) {
return "";
}
return std::accumulate(std::begin(range) + 1, std::end(range), std::ostringstream{} << *std::begin(range), [seperator](auto&& lhs, auto&& rhs) { return lhs << seperator << rhs; }).str();
}
Run Code Online (Sandbox Code Playgroud)
上面没有编译,并且有点“天真”的形式,但我认为它突出了“问题”。
编译器资源管理器链接中的错误:
<source>(13): error C2280: 'std::basic_ostream<char,std::char_traits<char>>::basic_ostream(const std::basic_ostream<char,std::char_traits<char>> &)': attempting to reference a deleted function
C:/data/msvc/14.22.27905/include\ostream(57): note: see declaration of 'std::basic_ostream<char,std::char_traits<char>>::basic_ostream'
C:/data/msvc/14.22.27905/include\ostream(57): note: 'std::basic_ostream<char,std::char_traits<char>>::basic_ostream(const std::basic_ostream<char,std::char_traits<char>> &)': function was explicitly deleted
C:/data/msvc/14.22.27905/include\numeric(72): note: see reference to function template instantiation 'std::basic_ostream<char,std::char_traits<char>> strjoin::<lambda_d85bd1f8d5f8c34784482fe135d50702>::operator …
Run Code Online (Sandbox Code Playgroud) 我看到一些inline const
变量被Visual Studio 2017初始化(和破坏)3次的例子.这是链接器的错误吗?或者这应该以其他方式发生?
链接器Comdat折叠设置为关闭.
示例代码:
#pragma once
struct A {
A() {
static int count = 0;
++count;
ASSERT(count == 1);
}
~A() {
}
};
inline const A a = A();
Run Code Online (Sandbox Code Playgroud)
在我的解决方案中,我有两次断言(一个构造函数被称为3次).检查调用堆栈显示所有调用堆栈都是相同的,并且所有调用都来自()的动态初始化程序.现在我知道这个类没有用在解决方案的其他部分,因为我刚创建它来调查这个问题.
我使用VS17 15.8.9
更新:此处的错误报告https://developercommunity.visualstudio.com/content/problem/297876/static-inline-variable-gets-destroyed-multiple-tim.html(您可以通过upvote来帮助推送错误修正)
以下给出了编译器错误:
#include <string>
const std::string& get_name();
int main(){
auto&& name1 = get_name();//should bind to whatever
const auto& name2 = get_name();//also ok
const auto&& name3 = get_name();//<-not ok, why ?
return 0;
}
Run Code Online (Sandbox Code Playgroud)
链接到Godbolt:https://godbolt.org/z/l6IQQ7
如果我使用const auto&
它可以编译-但这不会绑定到值。
auto&&
将绑定到任何东西,以便自然也可以工作。但是,const auto&&
在这种情况下不绑定背后的逻辑是什么?我知道auto&&
会保留constness-但是有没有办法使之const
明确,同时又与引用/值无关?
动机:
对于函数等内部的“正常编程工作”,可以说类似这样的东西很棒:“我不在乎它是值还是引用-但我不会在其余函数中更改它”。
给定当前语言,这应该是可能的。
相关问题: 为什么添加const会使通用引用成为右值
我正在尝试改进异常诊断(更像是基本的崩溃处理),对于某些情况SetUnhandledExceptionFilter
(https://msdn.microsoft.com/en-us/library/windows/desktop/ms680634(v=vs.85).aspx)不'似乎有助于捕获致命错误。这种情况是当关闭并且不同的 atexit 函数和单例析构函数等正在运行(清理)时。另外,析构函数由于 noexcept 声明不匹配而终止的情况也值得关注。
使用AddVectoredExceptionHandler
(https://msdn.microsoft.com/en-us/library/windows/desktop/ms679274(v=vs.85).aspx)确实似乎是一个不错的选择,因为它的功能更像是调试器的“第一次机会”异常”,但是它也因此在太多情况下被调用(还有正常异常、某些信号等)。
我的问题如下:为了确定 Windows 平台上的两个路径是否相同,比较路径时不区分大小写,ei。“C:\test.txt”和“C:\Test.txt”解析为相同的文件元素。我可以通过使用std::filesystem::equal
示例轻松解决这个问题,但对于这个特定问题,我想在操作系统往返上节省一点(在空闲状态下运行并在每个循环上进行 100 多次比较 - 我担心它会很明显)
using path = std::filesystem::path;
const bool result = (path("C:\\test.txt").lexically_normal().make_preferred().native() == path("C:\\Test.txt").lexically_normal().make_preferred().native());
Run Code Online (Sandbox Code Playgroud)
在比较时std::filesystem::path
,即使通过调用进行词法规范化lexical_normal
也是以通用方式完成的,因此也会考虑这种情况。这当然是有道理的,但除了我自己进行字符串比较之外,我看不到一种方法可以在不进行比较的情况下使用库来执行此操作:是否有可能以某种方式覆盖路径的比较方式?
我也调查过boost::filesystem
,但据我所知也没有解决这个问题。
c++ ×10
c++17 ×9
accumulate ×1
algorithm ×1
c++-faq ×1
class-template-argument-deduction ×1
exception ×1
factory ×1
string ×1
templates ×1
terminate ×1
visual-c++ ×1