小编sig*_*igy的帖子

将double转换为string to double throws exception

以下代码在Visual Studio 2013中抛出std :: out_of_range异常,在我看来它不应该:

#include <string>
#include <limits>

int main(int argc, char ** argv)
{
    double maxDbl = std::stod(std::to_string(std::numeric_limits<double>::max()));

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

我也用gcc 4.9.2测试了代码,并且它没有抛出异常.该问题似乎是由转换为字符串后的字符串表示不准确引起的.在Visual Studio中std::to_string(std::numeric_limits<double>::max())产生

179769313486231610000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000.000000

这确实看起来太大了.然而,在gcc中,它会产生

179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858368.000000

这似乎小于传递的值.

但是,不std::numeric_limits<double>::max()应该归还

最大有限可表示的浮点数?

那么为什么字符串表示会出现呢?我在这里错过了什么?

c++ gcc type-conversion visual-studio

8
推荐指数
1
解决办法
716
查看次数

使用谷歌测试进行数据驱动的单元测试

我目前正在使用googles单元测试框架为嵌入式应用程序编写单元测试.现在我的老板很不高兴我测试的数据(即我调用被测试类的方法的值)在测试中是硬接线的.他要求从文件中读取此数据.他的论点是,为一个以前被遗忘的角落案件添加另一个测试会更容易.我不是单位测试的经验,但到目前为止,我不是这样做的.所以我试着弄清楚最好的方法是什么 - 即使这样做是个好主意.我很快就遇到了DDT(数据驱动测试)方法.

谷歌单元测试框架有一个他们称之为" 价值参数化测试 "的功能.有了它,我的测试夹具成为模板类,我可以传入参数.但是,我看到了一些问题:

  • 我目前每个班级都有一个夹具正在测试中.但是我需要每个测试方法都有一个夹具,因为每个方法都需要一组不同的参数.这将是一项额外的工作.
  • 在我看来,我只能传入一个参数.因为我的测试需要几个(我的方法的所有参数加上预期的结果)这需要我传递类似矢量或地图的东西.同样,这种构造和检索听起来像很多工作.

我会想象像谷歌测试框架那样成熟的东西让它变得更容易.但是,他们写道

值参数化测试很方便[当]你想通过各种输入(又称数据驱动测试)测试你的代码.此功能很容易被滥用,所以请在锻炼时锻炼你的良好感觉!

此外还有这篇博客文章TotT:Data Driven Traps,也警告我(滥用)数据驱动的单元测试.

所以我的问题归结为:

  • 进行数据驱动的单元测试是个好主意吗?
  • 如何使用谷歌测试框架进行数据驱动的单元测试

我并不是真的要googletest,而且基本上可以自由选择任何我喜欢的框架.

编辑

我在googletest常见问题解答的FAQ条目中找到了以下声明

一般来说,Google Test对数据驱动的测试还没有很好的支持.我们希望很快能够在这方面做出改进.

c++ testing unit-testing googletest data-driven-tests

8
推荐指数
1
解决办法
3722
查看次数

如何在Vista/Server 2008上使用std :: shared_mutex?

这是TryAcquireSRWLock*和_WIN32_WINNT的后续问题

由于Windows SDK 8.1及更新版本(至少目前为10.0.16299.0)中存在一个错误,因此可以使用针对Windows Vista或Windows Server 2008的编译方法TryAcquireSRWLockSharedTryAcquireSRWLockExclusive.这会导致应用程序包含对这些方法的调用无法在Windows Vista或Windows Server 2008上执行,因为它们最终只能从Windows 7或Windows Server 2008 R2开始提供.

似乎Windows SDK 8.1 中std :: shared_mutex的实现使用了TryAcquireSRWLockSharedTryAcquireSRWLockExclusive.因此,使用std :: shared_mutex会导致应用程序无法在Windows Vista或Windows Server 2008上执行.

文档还说明

警告

从Visual Studio 2015开始,C++标准库同步类型基于Windows同步原语,不再使用ConcRT(目标平台为Windows XP时除外).<shared_mutex>中定义的类型不应与任何ConcRT类型或函数一起使用.

但是,当使用平台工具集v140_xp时,编译器会抱怨根本不知道std :: shared_mutex.

如何使用std :: shared_mutex并仍然以Windows Vista或Windows Server 2008为目标?

c++ windows winapi c++17

8
推荐指数
1
解决办法
172
查看次数

确保派生类实现静态方法

我想确保派生类实现一个特定的静态方法.我认为这样做应该可以使用static_assert,std :: is_same,decltype,CRTP并且可能使用SFINAE.但是,到目前为止,我发现的类似代码非常复杂,似乎我还没有完全理解它使我无法将其用于我的需求.

到目前为止我尝试过的是这个

template <class T>
class Base 
{
    static_assert(std::is_same<decltype(T::foo(1)), int>::value, "ERROR STRING");
};

class Derived : public Base <Derived>
{
public:
    static int foo(int i) { return 42; };
};
Run Code Online (Sandbox Code Playgroud)

但是,它没有编译告诉我,即使方法正确实现,Derived也没有名为foo的元素.此外,在static_assert内的表达式中为foo提供实际参数会感觉不对.

搜索SO揭示了一个类似的问题,最终引导我到这段代码,检查一个类型有方法begin()和end()返回迭代器.所以我试着采用这个代码来满足我的需求.

template <class T>
class Base 
{
    template<typename C>
    static char(&g(typename std::enable_if<std::is_same<decltype(static_cast<int(C::*)(int)>(&C::foo)), int(C::*)(int)>::value, void>::type*))[1];

    template<typename C>
    static char(&g(...))[2];

    static_assert(sizeof(g<T>(0)) == 1, "ERROR STRING");
};
Run Code Online (Sandbox Code Playgroud)

但是这段代码没有编译,因为断言触发了.

所以我的问题是

  1. 为什么编译器在我的第一个例子中找不到Derived :: foo?
  2. typename C::const_iterator(C::*)() const示例代码到底意味着什么?是不是一个const函数返回C …

c++ static-assert crtp type-traits c++11

7
推荐指数
1
解决办法
774
查看次数

了解lcov分支覆盖输出中的控制流图

我正在尝试通过检查我当前的代码覆盖百分比来改进我的单元测试.我正在使用gcov和lcov生成覆盖结果的HTML报告.但是,我在理解某些输出时遇到了问题.我知道a +表示已经采取了分支并且-没有采取分支.

131                 :          8 :         QString toString() const
132                 :            :         {
133 [ +  - ][ +  - ]:          8 :             return ((negative && !isZero()) ? "-" : "") + QString::number(sec) + "." + QString::number(nano).rightJustified(9, '0');
    [ +  - ][ +  + ]
    [ +  - ][ +  - ]
    [ +  - ][ +  - ]
            [ +  - ]
134                 :            :         }
Run Code Online (Sandbox Code Playgroud)

变量negative的类型为bool,因为是方法的返回值isZero.所以我希望这里有四个分支,但我不知道输出如何映射到这个期望.那么如何解释输出?悬停在+/-标志上时的工具提示告诉我分支3,6,9,11,12,14,17,20,23和26是在分支4,7,10,15,18,21,24和27人从未被带走过.

c++ code-coverage gcov lcov control-flow-graph

6
推荐指数
1
解决办法
491
查看次数

基于参数在基类中创建派生类

我的问题或多或少与需要一个设计模式去除对象创建中的枚举和切换语句的问题相同但是我没有看到抽象工厂模式适合这里.

我目前正计划对一些现有的DAL/ORM混合库进行重构/重新实现.在现有代码中的某处,代码如下所示:

class Base
{
  static Base * create(struct Databasevalues dbValues)
  {
    switch(dbValues.ObjectType)
    {
    case typeA:
      return new DerivedA(dbValues);
      break;
    case typeB:
      return new DerivedB(dbValues);
      break;
    }
  }
}

class DerivedA : public Base
{
  // ...
}

class DerivedB : public Base
{
  // ...
}
Run Code Online (Sandbox Code Playgroud)

因此,负责数据库通信的库使用有关数据库实体的所有信息填充结构,然后调用上述create()方法以在ORM中实际创建相应的对象.但我不喜欢基类知道所有派生类的想法,我也不喜欢switch语句.我还想避免创建另一个类只是为了创建这些对象.您如何看待当前的方法?你会如何实现这个功能?

c++ design-patterns derived-class object-construction

4
推荐指数
1
解决办法
3318
查看次数

将python嵌入到我的应用程序中时内存泄漏

以下程序,当链接到python 2.7.13并在Windows 10上运行缓慢但稳定地泄漏内存.

#include <Python.h>
#include <iostream>

int main()
{
    std::cout << "Python version: " << PY_VERSION << std::endl;

    while (true)
    {
        Py_Initialize();
        //PyGC_Collect();
        Py_Finalize();
    }

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

有趣的是,似乎并非每次迭代都会泄漏内存.但我所看到的是,无论泄漏如何,python打印缓慢的引用计数增加了每次迭代大约90次的(非常量)计数.使用Visual Studio诊断工具我发现泄漏来自于PyImport_ImportModule()从磁盘读取已编译模块时的调用(实际调用堆栈深度为几级).

是否还需要我不知道的额外清理步骤?或者有什么关于Python垃圾收集器可能导致这一点,它不是一个"真正的"内存泄漏?

c++ python memory-leaks cpython python-c-api

2
推荐指数
1
解决办法
524
查看次数

我可以从不同的线程访问 COM 对象的接口吗?

我可以在服务的主工作线程中访问IAudioEndpointVolume接口,如下所示(省略错误检查):

CoInitialize(NULL);
CoCreateGuid(&g_guidMyContext);
CoCreateInstance(CLSID_MMDeviceEnumerator, NULL, CLSCTX_INPROC_SERVER, IID_IMMDeviceEnumerator, (void**)&m_pEnumerator);

IMMDevice *pEndpoint = NULL;
m_pEnumerator->GetDevice(&deviceID[0], &pEndpoint);

IAudioEndpointVolume *pAudioVol = NULL;
pEndpoint->Activate(__uuidof(IAudioEndpointVolume), CLSCTX_ALL, NULL, (void**)&pAudioVol);

CAudioEndpointVolumeCallback *pVolumeCallback = new CAudioEndpointVolumeCallback(pAudioVol, 100, TRUE, m_debugLog, m_logMutex);
Run Code Online (Sandbox Code Playgroud)

CAudioEndpointVolumeCallback然后,该类将IAudioEndpointVolume指针存储在成员变量中,并RegisterControlChangeNotify(this)在其构造函数中调用它。

该类还可以启动一个线程,以便在短时间内将音量从一个值平滑地更改为另一个值。所以最后我打电话给IAudioEndpointVolume从不同的线程调用接口。总的来说,所有这些都按预期工作,但在某些边缘情况下我遇到了一些奇怪的行为。当再次检查代码时,我偶然发现了 MSDN 文档中有关线程的注释(我之前没有任何 COM 对象的经验),并想知道我所做的是否正确。

IAudioEndpointVolume那么,使用上面的代码从不同线程调用接口是否安全?我是否必须使用互斥锁来保护这些调用?

我有点困惑,不确定我是否真正理解COM 线程模型的行为

c++ com winapi multithreading

1
推荐指数
1
解决办法
835
查看次数

是否可以在不更改提交的哈希值的情况下压缩提交?

我忘了将文件添加到我已经推送的提交中并为其创建了拉取请求.拉取请求被拒绝(由于其他原因).我现在想要将丢失的文件添加到原始提交中,然后在发出新的拉取请求之前在新提交中执行请求的更改.但是,git rebase将遗留文件的提交压缩到旧文件中会更改提交的哈希值,从而导致对GitHub产生奇怪的影响.有没有办法做我正在尝试或我必须让丢失的文件在自己的提交?

我是唯一使用我的存储库的人.Pull请求是对其他用户的唯一引用.

git github rebase squash

1
推荐指数
1
解决办法
919
查看次数

gitlab-ctl重新配置:无法确定节点名称

我确实在Ubuntu 16.04.4 LTS上设置了一个新的GitLab实例。安装软件包运行正常,并且GitLab似乎已启动并正在运行。然后,我开始在中配置实例并设置SMTP /etc/gitlab/gitlab.rb。之后我跑了sudo gitlab-ctl reconfigure。它失败,并显示以下错误消息:

Starting Chef Client, version 13.6.4

Running handlers:
There was an error running gitlab-ctl reconfigure:

Unable to determine node name: configure node_name or configure the system's hostname and fqdn

Running handlers complete
Chef Client failed. 0 resources updated in 10 seconds
Run Code Online (Sandbox Code Playgroud)

设置系统的主机名和fqdn:

$ hostname --fqdn
git-lab.dom
$ hostname
git-lab
Run Code Online (Sandbox Code Playgroud)

Ohai似乎成功读取了主机名,fqdn和域:

$ /opt/gitlab/embedded/bin/ohai
[...]
"hostname": "git-lab",
"machinename": "git-lab",
"fqdn": "git-lab.dom",
"domain": "dom",
[...]
Run Code Online (Sandbox Code Playgroud)

对于类似问题答案建议手动设置node_namein /etc/chef/client.rb。但是,gitlab omnibus软件包似乎将client.rb放在其他位置。我也不愿意遵循这个建议,因为对于我来说到目前为止我还没有必须安装其他的GitLab,这对我来说似乎很奇怪。此外,文档指出(重点是我): …

chef-infra gitlab gitlab-omnibus

1
推荐指数
1
解决办法
1625
查看次数