2010-05-29 36 views
16

Tôi có một chương trình tạo biểu đồ bằng các mô hình đa cấp khác nhau. Mỗi mô hình đa cấp bao gồm một thế hệ của một biểu đồ hạt nhỏ hơn (có nghĩa là, 50 nút) có thể được tạo ra từ một số mô hình (ví dụ - cho mỗi cạnh có thể, chọn để bao gồm nó với xác suất p).Xử lý các tùy chọn phức tạp với các chương trình của Boost

Sau khi tạo biểu đồ hạt giống, biểu đồ được mở rộng thành hình lớn hơn (giả sử 1000 nút), sử dụng một trong các nhóm mô hình khác.

Trong mỗi giai đoạn, mỗi mô hình yêu cầu một số thông số khác nhau.

Tôi muốn có program_options phân tích cú pháp các thông số có thể khác nhau, theo tên của các mô hình.

Ví dụ: giả sử tôi có hai mô hình biểu đồ hạt giống: SA, có 1 tham số và SB, có hai tham số. Cũng cho phần mở rộng, tôi có hai mô hình: A và B, một lần nữa với các tham số 1 và 2, tương ứng. Tôi muốn có thể làm một việc gì đó như:

./graph_generator --seed=SA 0.1 --expansion=A 0.2 
./graph_generator --seed=SB 0.1 3 --expansion=A 0.2 
./graph_generator --seed=SA 0.1 --expansion=B 10 20 
./graph_generator --seed=SB 0.1 3 --expansion=B 10 20 

và có các tham số được phân tích cú pháp chính xác. Điều đó thậm chí có thể?

Trả lời

23

Bằng cách sử dụng một custom validatorboost::program_options::value::multitoken, bạn có thể đạt được kết quả mong muốn:

#include <iostream> 
#include <boost/lexical_cast.hpp> 
#include <boost/optional.hpp> 
#include <boost/program_options.hpp> 

// Holds parameters for seed/expansion model 
struct Model 
{ 
    std::string type; 
    boost::optional<float> param1; 
    boost::optional<float> param2; 
}; 

// Called by program_options to parse a set of Model arguments 
void validate(boost::any& v, const std::vector<std::string>& values, 
       Model*, int) 
{ 
    Model model; 
    // Extract tokens from values string vector and populate Model struct. 
    if (values.size() == 0) 
    { 
     throw boost::program_options::validation_error(
      "Invalid model specification"); 
    } 
    model.type = values.at(0); // Should validate for A/B 
    if (values.size() >= 2) 
     model.param1 = boost::lexical_cast<float>(values.at(1)); 
    if (values.size() >= 3) 
     model.param2 = boost::lexical_cast<float>(values.at(2)); 

    v = model; 
} 

int main(int argc, char* argv[]) 
{ 
    Model seedModel, expansionModel; 

    namespace po = boost::program_options; 
    po::options_description options("Generic options"); 
    options.add_options() 
     ("seed", 
      po::value<Model>(&seedModel)->multitoken(), 
      "seed graph model") 
     ("expansion", 
      po::value<Model>(&expansionModel)->multitoken(), 
      "expansion model") 
     ; 

    po::variables_map vm; 
    po::store(po::parse_command_line(argc, argv, options), vm); 
    po::notify(vm); 

    std::cout << "Seed type: " << seedModel.type << "\n"; 
    if (seedModel.param1) 
     std::cout << "Seed param1: " << *(seedModel.param1) << "\n"; 
    if (seedModel.param2) 
     std::cout << "Seed param2: " << *(seedModel.param2) << "\n"; 

    std::cout << "Expansion type: " << expansionModel.type << "\n"; 
    if (expansionModel.param1) 
     std::cout << "Expansion param1: " << *(expansionModel.param1) << "\n"; 
    if (expansionModel.param2) 
     std::cout << "Expansion param2: " << *(expansionModel.param2) << "\n"; 

    return 0; 
} 

Chức năng validate lẽ cần nghiêm khắc hơn, nhưng bạn sẽ có được ý tưởng.

Tính năng này biên dịch và hoạt động cho tôi.

Các vấn đề liên quan