我在C++中使用libcurl,并且我curl_easy_perform使用Boost.Thread在我的UI中调用一个单独的线程.
主UI有一个取消按钮,我想要完全响应(即,当用户点击它时,它应立即作出反应).我已经设置了读取,写入和进度回调来读取原子should_cancel变量(如本问题所示),但有两个问题:
从按下取消到卷曲操作完成时,通常会有非常小的(但明显的)延迟.
偶尔会有很长的(有时是无休止的)延迟.在这种情况下,要么:
一个.进度,读取和写入回调很长一段时间都没有被调用,或者
湾 进度回调被调用时,我返回一个非零值(这意味着它应该终止),但卷曲操作不一会儿完成更长(事实上,功能将被再次在此期间,被称为!)
所以:
一种可能性是告诉UI取消操作成功,但继续在后台运行curl线程,直到取消.这个问题(我认为)是它强制should_cancel变量是全局的,而不是作用于操作开始的对话框.
我打算写一个适配器类.在这个类中有一个xmlrpc-c服务器(深渊服务器).我想通过创建一个新线程来启动服务器,并且线程的功能是成员函数XMLThreadFun().
当我尝试使用下面的代码时,在适配器的构造函数实现的行上有一个错误:
/usr/include/boost/bind/bind.hpp:69:37: error: ‘void (Adapter::*)()’ is not a class, struct, or union type
Run Code Online (Sandbox Code Playgroud)
谁能告诉我如何解决这个错误,或者如何实现我的目标?对此,我真的非常感激.
以下是我的代码片段:
#ifdef _MSC_VER
#pragma warning( disable : 4503 4355 4786 )
#else
#include "config.h"
#endif
#include "quickfix/FileStore.h"
#include "quickfix/SocketInitiator.h"
#include "quickfix/SessionSettings.h"
#include "Application.h"
#include <string>
#include <iostream>
#include <fstream>
#include "quickfix/SessionID.h"
#include "quickfix/Session.h"
#include "getopt-repl.h"
#include <cassert>
#include <xmlrpc-c/base.hpp>
#include <xmlrpc-c/registry.hpp>
#include <xmlrpc-c/server_abyss.hpp>
#include <boost/thread.hpp>
#include <boost/date_time.hpp>
using namespace std;
class theClient : public xmlrpc_c::method {
public:
theClient() {}
theClient(FIX::SocketInitiator* initiator) {
set<FIX::SessionID> …Run Code Online (Sandbox Code Playgroud) 我的任务是修改同步C程序,以便它可以并行运行.我们的目标是让它尽可能便携,因为它是许多人使用的开源程序.因此,我认为最好将程序包装在C++层中,这样我就可以利用便携式的boost库.我已经完成了这一切,一切似乎按预期工作.
我遇到的问题是决定在线程之间传递消息的最佳方法是什么.幸运的是,该程序的体系结构是多生产者和单个消费者的体系结构.更好的是,消息的顺序并不重要.我已经读过单一生产者/单一消费者(SPSC)队列将受益于这种架构.那些有多线程编程经验的人有什么建议吗?我对这些东西很新.此外,任何使用boost实现SPSC的代码示例都将非常感激.
我有一个应用程序,需要在某些窗口内工作(在这种情况下,窗口相隔30秒).当时间不在窗口内时,计算下一个窗口中间的时间,并且线程休眠该时间量(以毫秒为单位,使用boost::this_thread::sleep_for).
使用Boost 1.55,我能够在极限可靠性的范围内(+/- 100ms)击中窗户.在迁移到Boost 1.58后,我无法打到这些窗口.替换boost::this_thread::sleep_forwith std::this_thread::sleep_for修复了问题; 但是,我需要提供的可中断功能boost::thread和中断点boost::this_thread::sleep_for.
以下是一些说明问题的示例代码:
#include <boost/thread.hpp>
#include <boost/chrono.hpp>
#include <chrono>
#include <iostream>
#include <thread>
void boostThreadFunction ()
{
std::cout << "Starting Boost thread" << std::endl;
for (int i = 0; i < 10; ++i)
{
auto sleep_time = boost::chrono::milliseconds {29000 + 100 * i};
auto mark = std::chrono::steady_clock::now ();
boost::this_thread::sleep_for (sleep_time);
auto duration = std::chrono::duration_cast<std::chrono::milliseconds>(
std::chrono::steady_clock::now () - mark);
std::cout << "Boost thread:" << std::endl;
std::cout << …Run Code Online (Sandbox Code Playgroud) 我尝试使用提升线程期货.如图所示,我们可以从打包任务中获得共享的未来.
所以我在linux上尝试这样的功能:
template <class task_return_t>
void pool_item( boost::shared_ptr< boost::packaged_task<task_return_t> > pt)
{
boost::shared_future<task_return_t> fi= pt->get_future(); // error
//...
Run Code Online (Sandbox Code Playgroud)
但我收到错误称:
../../src/cf-util/thread_pool.h: In member function ‘void thread_pool::pool_item(boost::shared_ptr<boost::packaged_task<R> >) [with task_return_t = void]’:
../../src/cf-util/thread_pool.h:64:3: instantiated from ‘void thread_pool::post(boost::shared_ptr<boost::packaged_task<R> >) [with task_return_t = void]’
../../src/cf-server/server.cpp:39:27: instantiated from here
../../src/cf-util/thread_pool.h:124:58: error: conversion from ‘boost::unique_future<void>’ to non-scalar type ‘boost::shared_future<void>’ requested
Run Code Online (Sandbox Code Playgroud)
我之前没有接受任何期货.所有的源代码,地方,我从打电话,那是被称为我的线程池.在Visual Studio 2010下的Windows上,它可以完美地编译和工作.
我该怎么办?如何修复或解决此错误?
我围绕boost :: asio :: io_service创建了一个包装器,以处理OpenGL应用程序的GUI线程上的异步任务。
任务可能是从其他线程创建的,因此boost::asio看来是理想的选择,这意味着我不需要编写带有关联互斥锁和锁定的任务队列。我想将每个帧上完成的工作保持在可接受的阈值(例如5毫秒)以下,因此我要打电话poll_one直到超出所需的预算为止,而不是打电话run。据我所知,这要求我reset在发布新任务时都打电话给我,这似乎效果很好。
由于很短,所以这里是整件事,无#include:
typedef std::function<void(void)> VoidFunc;
typedef std::shared_ptr<class UiTaskQueue> UiTaskQueueRef;
class UiTaskQueue {
public:
static UiTaskQueueRef create()
{
return UiTaskQueueRef( new UiTaskQueue() );
}
~UiTaskQueue() {}
// normally just hand off the results of std/boost::bind to this function:
void pushTask( VoidFunc f )
{
mService.post( f );
mService.reset();
}
// called from UI thread; defaults to ~5ms budget (but always does one call)
void update( const …Run Code Online (Sandbox Code Playgroud) 我正在尝试创建一个类,在创建时,启动一个后台线程,类似于下面的:
class Test
{
boost::thread thread_;
void Process()
{
...
}
public:
Test()
{
thread_ = boost::thread(Process);
}
}
Run Code Online (Sandbox Code Playgroud)
我无法编译,错误是"没有匹配函数调用boost :: thread :: thread(未解析的函数类型)".当我在课外做这件事时,它运作正常.如何让函数指针起作用?
我有一个使用Boost 1.47.0的Visual Studio 2008 C++项目,我需要将boost :: thread的本机Windows ID传递给PostThreadMessage.
在Windows Vista和7中,我会这样做:
DWORD thread_id = ::GetThreadId( mythread.native_handle() );
Run Code Online (Sandbox Code Playgroud)
这很好,但我还需要我的应用程序在GetThreadId不存在的XP中工作.
我发现boost:thread将线程ID值存储在boost :: thread :: id的私有数据成员中thread_data.我可以通过做一些讨厌的演员来达到这个目的:
boost::detail::thread_data_base* tdb = *reinterpret_cast< boost::detail::thread_data_base** >( &message_thread.get_id() );
DWORD thread_id = tdb->id;
Run Code Online (Sandbox Code Playgroud)
但是,我开始收到引用临时boost::thread::id对象的编译器警告.
warning C4238: nonstandard extension used : class rvalue used as lvalue
Run Code Online (Sandbox Code Playgroud)
有没有一个好方法来获取ID?看到我需要的数据非常令人沮丧,但却无法实现.
谢谢,PaulH
int func(boost::asio::ip::tcp::socket &socket)
{
boost::system::error_code ec;
socket.write_some(boost::asio::buffer("hello world!"), ec);
cout << socket.is_open() << endl;
if(ec)
{
cout << boost::system::system_error(ec).what() << endl;
}
return 0;
}
int main(int argc, char* argv[])
{
using namespace boost::asio;
io_service iosev;
ip::tcp::acceptor acceptor(iosev, ip::tcp::endpoint(ip::tcp::v4(), 1000));
while(1)
{
ip::tcp::socket socket(iosev);
acceptor.accept(socket);
boost::thread t = boost::thread(func, boost::ref(socket));
}
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我想要一个新线程处理新连接.但是在函数"func"中,socket没有打开,我得到了"Bad file descriptor".我在文档和Web中阅读了一些示例,但它们是异步的.我认为这对我的简单要求没有必要.
我该如何修复错误?任何帮助表示赞赏
我在使用boost中的共享内存对象,因为需要将内存页锁定到物理内存中的实时C++应用程序.在增强中我没有看到这样做的方法.我觉得我错过了一些东西,因为我知道Windows和Linux都有办法做到这一点(mlock()和VirtualLock()).
boost-thread ×10
c++ ×10
boost ×7
boost-asio ×2
curl ×1
future ×1
linux ×1
shared-ptr ×1
std-function ×1
windows ×1
xml-rpc ×1