1

简要背景:

我正在尝试使用QCustomPlot 1.3 beta 版绘制股票烛台图。我跳过了库的代码,发现对于时间序列,它使用了 type-def (qcustomplot.h:line 3140)

typedef QMap<double, QCPFinancialData> QCPFinancialDataMap;

QCPFinancialData在哪里(qcustomplot.h:line 3124)

class QCP_LIB_DECL QCPFinancialData
{
public:
  QCPFinancialData();
  QCPFinancialData(double key, double open, double high, double low, double close);
  double key, open, high, low, close;
};

因此,OHLC 数据显然在那里,并且该类使用 QMap 中使用的键来索引时间序列条目。

因此,显而易见的关键是日期时间(我正在绘制日终图表,所以每个条目只是一个日期,没有使用时间)。在我的解析代码中,我使用过

boost::gregorian::date

因为它有很多优点(从字符串转换、计算经过的日期时间等)。

问题是,我是否应该继续简单地将 boost::gregorian::date 转换为 unix 时间戳,然后将该时间戳记录为双精度?我在 github 上找到了一个小模板函数,可以将其转换为time_t类型,但我猜在这种情况下 double 应该不是问题,或者这是一个潜在的错误?AFAIK,Unix时间戳表示自1970年1月1日以来的秒数,当表示为双精度时,对于键来说应该绰绰有余?

在 QCustomPlot 的示例中,它们从时间序列序列(例如,开始日期)开始使用累加器/计数器,而不是时间戳。

4

1 回答 1

2

自纪元以来的时间戳可以非常方便地存储在双精度中,因为您有足够的空间存储自纪元以来的秒数(即 1970 年 1 月 1 日),并且仍然有足够的分辨率来存储超过一微秒的时间。

例如 R 这样做:

R> now <- Sys.time()                    # get current date and time
R> now                                  # default format to test
[1] "2014-11-11 20:38:27.307228 CST"    # NB I have an option set for subsec.
R> as.integer(now)                      # as integer: seconds since epoch
[1] 1415759907
R> as.double(now)                       # as double under default precision
[1] 1415759907
R> print(as.double(now), digits=16)     # as double with forced higher prec.
[1] 1415759907.307228
R> 

我一直double在 C/C++ 层使用这些。如果我没记错的话,您可以让 Boost 为您进行转换。

编辑:我知道我在某个地方有它:

boost::posix_time::ptime pt;        
// ... in what follows dt has subcomponents we can access
pt = boost::posix_time::ptime(boost::gregorian::date(dt.getYear(), 
                                                     dt.getMonth(), 
                                                     dt.getDay()), 
                              boost::posix_time::time_duration(dt.getHours(), 
                                                              dt.getMinutes(),
                                                              dt.getSeconds(), 
                                                 dt.getMicroSeconds()/1000.0));

转换为time_t包括亚秒:

boost::posix_time::ptime dt = .... 


boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1)); 
boost::posix_time::time_duration x = dt - epoch;  // needs UTC to local corr.,
                                                  // but we get the fract. sec.
struct tm t = boost::posix_time::to_tm(dt);       // this helps with UTC conve.
time_t tt = mktime(&t) + 1.0 * x.fractional_seconds() / x.ticks_per_second()));
于 2014-11-12T02:42:27.183 回答