<commit_before>// Copyright (C) 2012 Rhys Ulerich
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.

/** @file
 * Estimate the best AR(p) model given data on standard input.  Illustrates
 * \ref ar::autocorrelation, \ref ar::predictor,
 * and \ref ar::decorrelation_time.
 */

#include "ar.hpp"
#include "optionparser.h"

#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <fstream>
#include <functional>
#include <iomanip>
#include <iostream>
#include <iterator>
#include <limits>
#include <vector>

// Command line argument declarations for optionparser.h usage
enum OptionIndex { UNKNOWN, HELP, SUBMEAN, SIGNRHO };
const option::Descriptor usage[] = {
    {UNKNOWN, 0, "", "",      option::Arg::None,
     "Usage: arsel [OPTION]...\n"
     "Fit an optimal autoregressive model to data from standard input.\n"
     "\n"
     "Options:\n" },
    {SUBMEAN, 0,  "",  "subtract-mean", option::Arg::None,
     "\t--subtract-mean  \tSubtract the sample mean from the data" },
    {SIGNRHO, 0,  "",  "signed-rho",    option::Arg::None,
     "\t--signed-rho     \tUse autocorrelation, including sign, when computing T0" },
    {HELP,    0,  "h", "help",        option::Arg::None,
     "\t-h,--help        \tDisplay this help and exit" },
    {0,0,0,0,0,0}
};

int main(int argc, char *argv[])
{
    using namespace ar;
    using namespace std;

    // TODO Add processing of files specified on the command line

    // Process any incoming command line arguments using optionparser.h
    argc-=(argc>0); argv+=(argc>0); // Skip program name argv[0] if present
    option::Stats stats(usage, argc, argv);
    struct Guard { // scoped_array or unique_ptr would simply RAII here
        option::Option *options, *buffer;
        Guard(option::Option *options, option::Option *buffer)
            : options(options), buffer(buffer) {}
        ~Guard() { delete[] options; delete[] buffer; }
    } guard(new option::Option[stats.options_max],
            new option::Option[stats.buffer_max ]);
    option::Parser parse(usage, argc, argv, guard.options, guard.buffer);
    if (parse.error() || guard.options[UNKNOWN]) {
        for (option::Option* o = guard.options[UNKNOWN]; o; o = o->next()) {
            cout << "Unknown option: " << o->name << "\n";
        }
        return EXIT_FAILURE;
    }
    if (guard.options[HELP]) {
        option::printUsage(std::cout, usage);
        return EXIT_SUCCESS;
    }
    const bool subtract_mean = guard.options[SUBMEAN] ? true : false;
    const bool absolute_rho  = guard.options[SIGNRHO] ? false : true;

    // Use burg_method to estimate a hierarchy of AR models from input data
    double mean;
    size_t order = 512;
    vector<double> params, sigma2e, gain, autocor;
    params .reserve(order*(order + 1)/2);
    sigma2e.reserve(order + 1);
    gain   .reserve(order + 1);
    autocor.reserve(order + 1);
    const size_t N = burg_method(istream_iterator<double>(cin),
                                 istream_iterator<double>(),
                                 mean,
                                 order,
                                 back_inserter(params),
                                 back_inserter(sigma2e),
                                 back_inserter(gain),
                                 back_inserter(autocor),
                                 subtract_mean,
                                 /* output hierarchy? */ true);

    // Keep only best model according to CIC accounting for subtract_mean.
    if (subtract_mean) {
        best_model<CIC<Burg<mean_subtracted> > >(
                N, params, sigma2e, gain, autocor);
    } else {
        best_model<CIC<Burg<mean_retained> > >(
                N, params, sigma2e, gain, autocor);
    }

    // Compute decorrelation time from the estimated autocorrelation model
    const double T0  = decorrelation_time(N, autocorrelation(params.begin(),
                params.end(), gain[0], autocor.begin()), absolute_rho);

    // Output details about the best model and derived information
    // Unbiased effective variance expression from [Trenberth1984]
    cout.precision(numeric_limits<double>::digits10 + 2);
    cout << showpos
         <<   "# N                   "   << N
         << "\n# AR(p)               "   << params.size()
         << "\n# Mean                "   << mean
         << "\n# \\sigma^2_\\epsilon   " << sigma2e[0]
         << "\n# Variance_effective  "   << (N*gain[0]*sigma2e[0]) / (N - T0)
         << "\n# N_effective         "   << N / T0
         << "\n# t_decorrelation     "   << T0
         << '\n';
    copy(params.begin(), params.end(), ostream_iterator<double>(cout,"\n"));
    cout.flush();

    return EXIT_SUCCESS;
}
<commit_msg>error messages on stderr<commit_after>// Copyright (C) 2012 Rhys Ulerich
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.

/** @file
 * Estimate the best AR(p) model given data on standard input.  Illustrates
 * \ref ar::autocorrelation, \ref ar::predictor,
 * and \ref ar::decorrelation_time.
 */

#include "ar.hpp"
#include "optionparser.h"

#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <fstream>
#include <functional>
#include <iomanip>
#include <iostream>
#include <iterator>
#include <limits>
#include <vector>

// Command line argument declarations for optionparser.h usage
enum OptionIndex { UNKNOWN, HELP, SUBMEAN, SIGNRHO };
const option::Descriptor usage[] = {
    {UNKNOWN, 0, "", "",      option::Arg::None,
     "Usage: arsel [OPTION]...\n"
     "Fit an optimal autoregressive model to data from standard input.\n"
     "\n"
     "Options:\n" },
    {SUBMEAN, 0,  "",  "subtract-mean", option::Arg::None,
     "\t--subtract-mean  \tSubtract the sample mean from the data" },
    {SIGNRHO, 0,  "",  "signed-rho",    option::Arg::None,
     "\t--signed-rho     \tUse autocorrelation, including sign, when computing T0" },
    {HELP,    0,  "h", "help",        option::Arg::None,
     "\t-h,--help        \tDisplay this help and exit" },
    {0,0,0,0,0,0}
};

int main(int argc, char *argv[])
{
    using namespace ar;
    using namespace std;

    // TODO Add processing of files specified on the command line

    // Process any incoming command line arguments using optionparser.h
    argc-=(argc>0); argv+=(argc>0); // Skip program name argv[0] if present
    option::Stats stats(usage, argc, argv);
    struct Guard { // scoped_array or unique_ptr would simply RAII here
        option::Option *options, *buffer;
        Guard(option::Option *options, option::Option *buffer)
            : options(options), buffer(buffer) {}
        ~Guard() { delete[] options; delete[] buffer; }
    } guard(new option::Option[stats.options_max],
            new option::Option[stats.buffer_max ]);
    option::Parser parse(usage, argc, argv, guard.options, guard.buffer);
    if (parse.error() || guard.options[UNKNOWN]) {
        for (option::Option* o = guard.options[UNKNOWN]; o; o = o->next()) {
            cerr << "Unknown option: " << o->name << "\n";
        }
        return EXIT_FAILURE;
    }
    if (guard.options[HELP]) {
        option::printUsage(std::cout, usage);
        return EXIT_SUCCESS;
    }
    const bool subtract_mean = guard.options[SUBMEAN] ? true : false;
    const bool absolute_rho  = guard.options[SIGNRHO] ? false : true;

    // Use burg_method to estimate a hierarchy of AR models from input data
    double mean;
    size_t order = 512;
    vector<double> params, sigma2e, gain, autocor;
    params .reserve(order*(order + 1)/2);
    sigma2e.reserve(order + 1);
    gain   .reserve(order + 1);
    autocor.reserve(order + 1);
    const size_t N = burg_method(istream_iterator<double>(cin),
                                 istream_iterator<double>(),
                                 mean,
                                 order,
                                 back_inserter(params),
                                 back_inserter(sigma2e),
                                 back_inserter(gain),
                                 back_inserter(autocor),
                                 subtract_mean,
                                 /* output hierarchy? */ true);

    // Keep only best model according to CIC accounting for subtract_mean.
    if (subtract_mean) {
        best_model<CIC<Burg<mean_subtracted> > >(
                N, params, sigma2e, gain, autocor);
    } else {
        best_model<CIC<Burg<mean_retained> > >(
                N, params, sigma2e, gain, autocor);
    }

    // Compute decorrelation time from the estimated autocorrelation model
    const double T0  = decorrelation_time(N, autocorrelation(params.begin(),
                params.end(), gain[0], autocor.begin()), absolute_rho);

    // Output details about the best model and derived information
    // Unbiased effective variance expression from [Trenberth1984]
    cout.precision(numeric_limits<double>::digits10 + 2);
    cout << showpos
         <<   "# N                   "   << N
         << "\n# AR(p)               "   << params.size()
         << "\n# Mean                "   << mean
         << "\n# \\sigma^2_\\epsilon   " << sigma2e[0]
         << "\n# Variance_effective  "   << (N*gain[0]*sigma2e[0]) / (N - T0)
         << "\n# N_effective         "   << N / T0
         << "\n# t_decorrelation     "   << T0
         << '\n';
    copy(params.begin(), params.end(), ostream_iterator<double>(cout,"\n"));
    cout.flush();

    return EXIT_SUCCESS;
}
<|endoftext|>


<commit_before>/*
 * Copyright (c) 2011-2013 libbitcoin developers (see AUTHORS)
 *
 * This file is part of libbitcoin.
 *
 * libbitcoin is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License with
 * additional permissions to the one published by the Free Software
 * Foundation, either version 3 of the License, or (at your option)
 * any later version. For more information see LICENSE.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
 */
#include <boost/test/unit_test.hpp>
#include <bitcoin/bitcoin.hpp>

using namespace bc;

BOOST_AUTO_TEST_SUITE(format_tests)

// encode_hex/decode_hex

BOOST_AUTO_TEST_CASE(encode_test_odd_length_returns_empty)
{
    const auto& hex_str = "10a7fd15cb45bda9e90e19a15";
    BOOST_REQUIRE_EQUAL(encode_hex(decode_hex(hex_str)), "");
}

// TODO: these should be tested for correctness, not just round-tripping.

BOOST_AUTO_TEST_CASE(encode_test_round_trips)
{
    const auto& hex_str = "10a7fd15cb45bda9e90e19a15f";
    BOOST_REQUIRE_EQUAL(encode_hex(decode_hex(hex_str)), hex_str);
}

BOOST_AUTO_TEST_CASE(encode_test_padded_round_trips_value)
{
    const auto& unpadded_hex = "10a7fd15cb45bda9e90e19a15f";
    const auto& padded_hex = "  \n\t10a7fd15cb45bda9e90e19a15f\n  \t";
    BOOST_REQUIRE_EQUAL(encode_hex(decode_hex(padded_hex)), unpadded_hex);
}

// from_little_endian_unsafe/from_big_endian_unsafe/to_little_endian/to_big_endian

BOOST_AUTO_TEST_CASE(endian_test)
{
    auto le = to_little_endian<uint32_t>(123456789);
    BOOST_REQUIRE_EQUAL(from_little_endian_unsafe<uint32_t>(le.begin()),
        123456789u);

    auto be = to_big_endian<uint32_t>(123456789);
    BOOST_REQUIRE_EQUAL(from_big_endian_unsafe<uint32_t>(be.begin()),
        123456789u);

    std::reverse(le.begin(), le.end());
    BOOST_REQUIRE_EQUAL(from_big_endian_unsafe<uint32_t>(le.begin()),
        123456789u);

    auto bytes = data_chunk{ 0xff };
    BOOST_REQUIRE_EQUAL(from_big_endian_unsafe<uint8_t>(bytes.begin()),
        255u);

    auto quad = to_little_endian<uint64_t>(0x1122334455667788);
    BOOST_REQUIRE_EQUAL(from_little_endian_unsafe<uint64_t>(quad.begin()),
        0x1122334455667788u);
}

// btc_to_satoshi

BOOST_AUTO_TEST_CASE(btc_to_satoshi_0_btc_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0"));
    BOOST_REQUIRE_EQUAL(satoshi, 0u);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_decimal_point_only_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "."));
    BOOST_REQUIRE_EQUAL(satoshi, 0u);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_42_btc_test)
{
    uint64_t satoshi;
    uint64_t expected = 42 * coin_price(1);
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "42"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_max_money_test)
{
    uint64_t satoshi;
    uint64_t expected = max_money();
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "20999999.9769"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_overflow_precision_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(!btc_to_satoshi(satoshi, "0.999999999"));
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_no_leading_zero_test)
{
    uint64_t satoshi;
    uint64_t expected = coin_price(1) / 2;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, ".5"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_trailing_zero_test)
{
    uint64_t satoshi;
    uint64_t expected = coin_price(1) / 2;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0.50"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_offset_zero_test)
{
    uint64_t satoshi;
    uint64_t expected = coin_price(1) / 20;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0.05"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_max_int64_test)
{
    uint64_t satoshi;
    uint64_t expected = max_uint64;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "184467440737.09551615"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_overflow_int64_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(!btc_to_satoshi(satoshi, "184467440737.09551616"));
}

// satoshi_to_btc

BOOST_AUTO_TEST_CASE(satoshi_to_btc_0_satoshi_test)
{
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(0), "0");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_42_satoshi_test)
{
    uint64_t satoshi = 42 * coin_price(1);
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "42");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_max_money_test)
{
    uint64_t satoshi = max_money();
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "20999999.9769");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_overflow_max_money_test)
{
    uint64_t satoshi = max_money() + 1;
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "20999999.97690001");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_max_int64_test)
{
    uint64_t satoshi = max_uint64;
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "184467440737.09551615");
}

BOOST_AUTO_TEST_SUITE_END()<commit_msg>Add failing testcases for btc_to_satoshi<commit_after>/*
 * Copyright (c) 2011-2013 libbitcoin developers (see AUTHORS)
 *
 * This file is part of libbitcoin.
 *
 * libbitcoin is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License with
 * additional permissions to the one published by the Free Software
 * Foundation, either version 3 of the License, or (at your option)
 * any later version. For more information see LICENSE.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
 */
#include <boost/test/unit_test.hpp>
#include <bitcoin/bitcoin.hpp>

using namespace bc;

BOOST_AUTO_TEST_SUITE(format_tests)

// encode_hex/decode_hex

BOOST_AUTO_TEST_CASE(encode_test_odd_length_returns_empty)
{
    const auto& hex_str = "10a7fd15cb45bda9e90e19a15";
    BOOST_REQUIRE_EQUAL(encode_hex(decode_hex(hex_str)), "");
}

// TODO: these should be tested for correctness, not just round-tripping.

BOOST_AUTO_TEST_CASE(encode_test_round_trips)
{
    const auto& hex_str = "10a7fd15cb45bda9e90e19a15f";
    BOOST_REQUIRE_EQUAL(encode_hex(decode_hex(hex_str)), hex_str);
}

BOOST_AUTO_TEST_CASE(encode_test_padded_round_trips_value)
{
    const auto& unpadded_hex = "10a7fd15cb45bda9e90e19a15f";
    const auto& padded_hex = "  \n\t10a7fd15cb45bda9e90e19a15f\n  \t";
    BOOST_REQUIRE_EQUAL(encode_hex(decode_hex(padded_hex)), unpadded_hex);
}

// from_little_endian_unsafe/from_big_endian_unsafe/to_little_endian/to_big_endian

BOOST_AUTO_TEST_CASE(endian_test)
{
    auto le = to_little_endian<uint32_t>(123456789);
    BOOST_REQUIRE_EQUAL(from_little_endian_unsafe<uint32_t>(le.begin()),
        123456789u);

    auto be = to_big_endian<uint32_t>(123456789);
    BOOST_REQUIRE_EQUAL(from_big_endian_unsafe<uint32_t>(be.begin()),
        123456789u);

    std::reverse(le.begin(), le.end());
    BOOST_REQUIRE_EQUAL(from_big_endian_unsafe<uint32_t>(le.begin()),
        123456789u);

    auto bytes = data_chunk{ 0xff };
    BOOST_REQUIRE_EQUAL(from_big_endian_unsafe<uint8_t>(bytes.begin()),
        255u);

    auto quad = to_little_endian<uint64_t>(0x1122334455667788);
    BOOST_REQUIRE_EQUAL(from_little_endian_unsafe<uint64_t>(quad.begin()),
        0x1122334455667788u);
}

// btc_to_satoshi

BOOST_AUTO_TEST_CASE(btc_to_satoshi_0_btc_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0"));
    BOOST_REQUIRE_EQUAL(satoshi, 0u);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_decimal_point_only_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "."));
    BOOST_REQUIRE_EQUAL(satoshi, 0u);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_42_btc_test)
{
    uint64_t satoshi;
    uint64_t expected = 42 * coin_price(1);
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "42"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_max_money_test)
{
    uint64_t satoshi;
    uint64_t expected = max_money();
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "20999999.9769"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_overflow_precision_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(!btc_to_satoshi(satoshi, "0.999999999"));
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_no_leading_zero_test)
{
    uint64_t satoshi;
    uint64_t expected = coin_price(1) / 2;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, ".5"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_trailing_zero_test)
{
    uint64_t satoshi;
    uint64_t expected = coin_price(1) / 2;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0.50"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_offset_zero_test)
{
    uint64_t satoshi;
    uint64_t expected = coin_price(1) / 20;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0.05"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_max_int64_test)
{
    uint64_t satoshi;
    uint64_t expected = max_uint64;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "184467440737.09551615"));
    BOOST_REQUIRE_EQUAL(satoshi, expected);
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_overflow_int64_test)
{
    uint64_t satoshi;
    BOOST_REQUIRE(!btc_to_satoshi(satoshi, "184467440737.09551616"));
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_lexical_cast_fail)
{
    uint64_t satoshi;
    BOOST_REQUIRE(!btc_to_satoshi(satoshi, "0.-1"));
}

BOOST_AUTO_TEST_CASE(btc_to_satoshi_harmless_zeros)
{
    uint64_t satoshi;
    BOOST_REQUIRE(btc_to_satoshi(satoshi, "0.0000000100"));
    BOOST_REQUIRE_EQUAL(satoshi, 1);
}

// satoshi_to_btc

BOOST_AUTO_TEST_CASE(satoshi_to_btc_0_satoshi_test)
{
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(0), "0");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_42_satoshi_test)
{
    uint64_t satoshi = 42 * coin_price(1);
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "42");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_max_money_test)
{
    uint64_t satoshi = max_money();
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "20999999.9769");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_overflow_max_money_test)
{
    uint64_t satoshi = max_money() + 1;
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "20999999.97690001");
}

BOOST_AUTO_TEST_CASE(satoshi_to_btc_max_int64_test)
{
    uint64_t satoshi = max_uint64;
    BOOST_REQUIRE_EQUAL(satoshi_to_btc(satoshi), "184467440737.09551615");
}

BOOST_AUTO_TEST_SUITE_END()
<|endoftext|>


<commit_before>#ifndef ATOMIC_HH
#define ATOMIC_HH

#include <pthread.h>
#include <queue>
#include <sched.h>

#include "callbacks.hh"
#include "locks.hh"

#define MAX_THREADS 100

template<typename T>
class ThreadLocal {
public:
    ThreadLocal(void (*destructor)(void *) = NULL) {
        int rc = pthread_key_create(&key, destructor);
        if (rc != 0) {
            throw std::runtime_error("Failed to create a thread-specific key");
        }
    }

    ~ThreadLocal() {
        pthread_key_delete(key);
    }

    void set(const T &newValue) {
        pthread_setspecific(key, newValue);
    }

    T get() const {
        return reinterpret_cast<T>(pthread_getspecific(key));
    }

    void operator =(const T &newValue) {
        set(newValue);
    }

    operator T() const {
        return get();
    }

private:
    pthread_key_t key;
};

template <typename T>
class ThreadLocalPtr : public ThreadLocal<T*> {
public:
    ThreadLocalPtr(void (*destructor)(void *) = NULL) : ThreadLocal<T*>(destructor) {}

    ~ThreadLocalPtr() {}

    T *operator ->() {
        return ThreadLocal<T*>::get();
    }

    T operator *() {
        return *ThreadLocal<T*>::get();
    }

    void operator =(T *newValue) {
        set(newValue);
    }
};

template <typename T>
class Atomic {
public:

    Atomic(const T &initial = 0) {
        set(initial);
    }

    ~Atomic() {}

    T get() const {
        return value;
    }

    void set(const T &newValue) {
        value = newValue;
        __sync_synchronize();
    }

    operator T() const {
        return get();
    }

    void operator =(const T &newValue) {
        set(newValue);
    }

    bool cas(const T &oldValue, const T &newValue) {
        return __sync_bool_compare_and_swap(&value, oldValue, newValue);
    }

    T operator ++() { // prefix
        return __sync_add_and_fetch(&value, 1);
    }

    T operator ++(int ignored) { // postfix
        (void)ignored;
        return __sync_fetch_and_add(&value, 1);
    }

    T operator --() { // prefix
        return __sync_add_and_fetch(&value, -1);
    }

    T operator --(int ignored) { // postfix
        (void)ignored;
        return __sync_fetch_and_add(&value, -1);
    }

    T operator +=(T increment) {
        // Returns the new value
        return __sync_add_and_fetch(&value, increment);
    }

    T operator -=(T decrement) {
        return __sync_add_and_fetch(&value, -decrement);
    }

    T incr(const T &increment) {
        // Returns the old value
        return __sync_fetch_and_add(&value, increment);
    }

    T decr(const T &decrement) {
        return __sync_add_and_fetch(&value, -decrement);
    }

    T swap(const T &newValue) {
        T rv;
        while (true) {
            rv = get();
            if (cas(rv, newValue)) {
                break;
            }
        }
        return rv;
    }

    T swapIfNot(const T &badValue, const T &newValue) {
        T oldValue;
        while (true) {
            oldValue = get();
            if (oldValue != badValue) {
                if (cas(oldValue, newValue)) {
                    break;
                }
            } else {
                break;
            }
        }
        return oldValue;
    }
private:
    volatile T value;
};

template <typename T>
class AtomicPtr : public Atomic<T*> {
public:
    AtomicPtr(T *initial = NULL) : Atomic<T*>(initial) {}

    ~AtomicPtr() {}

    T *operator ->() {
        return Atomic<T*>::get();
    }

    T operator *() {
        return *Atomic<T*>::get();
    }

    operator bool() const {
        return Atomic<T*>::get() != NULL;
    }

    bool operator !() const {
        return  Atomic<T*>::get() == NULL;
    }
};

class SpinLock {
public:
    SpinLock() : lock(0) {}

    bool tryAcquire() {
        return __sync_lock_test_and_set(&lock, 1) == 0;
    }

    void acquire() {
        while (!tryAcquire()) {
            sched_yield();
        }
    }

    void release() {
        __sync_lock_release(&lock);
    }

private:
    volatile int lock;
    DISALLOW_COPY_AND_ASSIGN(SpinLock);
};

class SpinLockHolder {
public:
    SpinLockHolder(SpinLock *theLock) : sl(theLock) {
        lock();
    }

    ~SpinLockHolder() {
        unlock();
    }

    void lock() {
        sl->acquire();
        locked = true;
    }

    void unlock() {
        if (locked) {
            sl->release();
            locked = false;
        }
    }
private:
    SpinLock *sl;
    bool locked;
};

template <class T> class RCPtr;

class RCValue {
public:
    RCValue() : _rc_refcount(0) {}
    RCValue(const RCValue &other) : _rc_refcount(0) {(void)other;}
    ~RCValue() {}
private:
    template <class TT> friend class RCPtr;
    int _rc_incref() {
        return ++_rc_refcount;
    }

    int _rc_decref() {
        return --_rc_refcount;
    }

    Atomic<int> _rc_refcount;
};

template <class C>
class RCPtr {
public:
    RCPtr(C *init = NULL) : value(init) {
        if (init != NULL) {
            static_cast<RCValue *>(value)->_rc_incref();
        }
    }

    RCPtr(RCPtr<C> &other) : value(other.gimme()) {}

    ~RCPtr() {
        if (value && static_cast<RCValue *>(value)->_rc_decref() == 0) {
            delete value;
        }
    }

    void reset(C *newValue = NULL) {
        if (newValue != NULL) {
            static_cast<RCValue *>(newValue)->_rc_incref();
        }
        swap(newValue);
    }

    void reset(RCPtr<C> &other) {
        swap(other.gimme());
    }

    bool cas(RCPtr<C> &oldValue, RCPtr<C> &newValue) {
        SpinLockHolder lh(&lock);
        if (value == oldValue.get()) {
            C *tmp = value;
            value = newValue.gimme();
            if (tmp != NULL &&
                static_cast<RCValue *>(tmp)->_rc_decref() == 0) {
                lh.unlock();
                delete tmp;
            }
            return true;
        }
        return false;
    }

    // safe for the lifetime of this instance
    C *get() {
        return value;
    }

    C *operator =(RCPtr<C> &other) {
        reset(other);
    }

    C &operator *() const {
        return *value;
    }

    C *operator ->() const {
        return value;
    }

    bool operator! () const {
        return !value;
    }

    operator bool () const {
        return (bool)value;
    }

private:
    C *gimme() {
        SpinLockHolder lh(&lock);
        if (value) {
            static_cast<RCValue *>(value)->_rc_incref();
        }
        return value;
    }

    void swap(C *newValue) {
        SpinLockHolder lh(&lock);
        C *tmp(value.swap(newValue));
        lh.unlock();
        if (tmp != NULL && static_cast<RCValue *>(tmp)->_rc_decref() == 0) {
            delete tmp;
        }
    }

    AtomicPtr<C> value;
    SpinLock lock; // exists solely for the purpose of implementing reset() safely
};

template <typename T>
class AtomicQueue {
public:
    AtomicQueue() : counter((size_t)0), numItems((size_t)0) {}

    ~AtomicQueue() {
        size_t i;
        for (i = 0; i < counter; ++i) {
            delete queues[i];
        }
    }

    void push(T value) {
        std::queue<T> *q = swapQueue(); // steal our queue
        q->push(value);
        ++numItems;
        q = swapQueue(q);
    }

    void pushQueue(std::queue<T> &inQueue) {
        std::queue<T> *q = swapQueue(); // steal our queue
        numItems.incr(inQueue.size());
        while (!inQueue.empty()) {
            q->push(inQueue.front());
            inQueue.pop();
        }
        q = swapQueue(q);
    }

    void getAll(std::queue<T> &outQueue) {
        std::queue<T> *q(swapQueue()); // Grab my own queue
        std::queue<T> *newQueue(NULL);
        int count(0);

        // Will start empty unless this thread is adding stuff
        while (!q->empty()) {
            outQueue.push(q->front());
            q->pop();
            ++count;
        }

        size_t c(counter);
        for (size_t i = 0; i < c; ++i) {
            // Swap with another thread
            newQueue = queues[i].swapIfNot(NULL, q);
            // Empty the queue
            if (newQueue != NULL) {
                q = newQueue;
                while (!q->empty()) {
                    outQueue.push(q->front());
                    q->pop();
                    ++count;
                }
            }
        }

        q = swapQueue(q);
        numItems -= count;
    }

    size_t getNumQueues() const {
        return counter;
    }

    bool empty() const {
        return size() == 0;
    }

    size_t size() const {
        return numItems;
    }
private:
    AtomicPtr<std::queue<T> > *initialize() {
        std::queue<T> *q = new std::queue<T>;
        size_t i(counter++);
        queues[i] = q;
        threadQueue = &queues[i];
        return &queues[i];
    }

    std::queue<T> *swapQueue(std::queue<T> *newQueue = NULL) {
        AtomicPtr<std::queue<T> > *qPtr(threadQueue);
        if (qPtr == NULL) {
            qPtr = initialize();
        }
        return qPtr->swap(newQueue);
    }

    ThreadLocalPtr<AtomicPtr<std::queue<T> > > threadQueue;
    AtomicPtr<std::queue<T> > queues[MAX_THREADS];
    Atomic<size_t> counter;
    Atomic<size_t> numItems;
    DISALLOW_COPY_AND_ASSIGN(AtomicQueue);
};

#endif // ATOMIC_HH
<commit_msg>Some const-correctness in atomic.hh<commit_after>#ifndef ATOMIC_HH
#define ATOMIC_HH

#include <pthread.h>
#include <queue>
#include <sched.h>

#include "callbacks.hh"
#include "locks.hh"

#define MAX_THREADS 100

template<typename T>
class ThreadLocal {
public:
    ThreadLocal(void (*destructor)(void *) = NULL) {
        int rc = pthread_key_create(&key, destructor);
        if (rc != 0) {
            throw std::runtime_error("Failed to create a thread-specific key");
        }
    }

    ~ThreadLocal() {
        pthread_key_delete(key);
    }

    void set(const T &newValue) {
        pthread_setspecific(key, newValue);
    }

    T get() const {
        return reinterpret_cast<T>(pthread_getspecific(key));
    }

    void operator =(const T &newValue) {
        set(newValue);
    }

    operator T() const {
        return get();
    }

private:
    pthread_key_t key;
};

template <typename T>
class ThreadLocalPtr : public ThreadLocal<T*> {
public:
    ThreadLocalPtr(void (*destructor)(void *) = NULL) : ThreadLocal<T*>(destructor) {}

    ~ThreadLocalPtr() {}

    T *operator ->() {
        return ThreadLocal<T*>::get();
    }

    T operator *() {
        return *ThreadLocal<T*>::get();
    }

    void operator =(T *newValue) {
        set(newValue);
    }
};

template <typename T>
class Atomic {
public:

    Atomic(const T &initial = 0) {
        set(initial);
    }

    ~Atomic() {}

    T get() const {
        return value;
    }

    void set(const T &newValue) {
        value = newValue;
        __sync_synchronize();
    }

    operator T() const {
        return get();
    }

    void operator =(const T &newValue) {
        set(newValue);
    }

    bool cas(const T &oldValue, const T &newValue) {
        return __sync_bool_compare_and_swap(&value, oldValue, newValue);
    }

    T operator ++() { // prefix
        return __sync_add_and_fetch(&value, 1);
    }

    T operator ++(int ignored) { // postfix
        (void)ignored;
        return __sync_fetch_and_add(&value, 1);
    }

    T operator --() { // prefix
        return __sync_add_and_fetch(&value, -1);
    }

    T operator --(int ignored) { // postfix
        (void)ignored;
        return __sync_fetch_and_add(&value, -1);
    }

    T operator +=(T increment) {
        // Returns the new value
        return __sync_add_and_fetch(&value, increment);
    }

    T operator -=(T decrement) {
        return __sync_add_and_fetch(&value, -decrement);
    }

    T incr(const T &increment) {
        // Returns the old value
        return __sync_fetch_and_add(&value, increment);
    }

    T decr(const T &decrement) {
        return __sync_add_and_fetch(&value, -decrement);
    }

    T swap(const T &newValue) {
        T rv;
        while (true) {
            rv = get();
            if (cas(rv, newValue)) {
                break;
            }
        }
        return rv;
    }

    T swapIfNot(const T &badValue, const T &newValue) {
        T oldValue;
        while (true) {
            oldValue = get();
            if (oldValue != badValue) {
                if (cas(oldValue, newValue)) {
                    break;
                }
            } else {
                break;
            }
        }
        return oldValue;
    }
private:
    volatile T value;
};

template <typename T>
class AtomicPtr : public Atomic<T*> {
public:
    AtomicPtr(T *initial = NULL) : Atomic<T*>(initial) {}

    ~AtomicPtr() {}

    T *operator ->() {
        return Atomic<T*>::get();
    }

    T operator *() {
        return *Atomic<T*>::get();
    }

    operator bool() const {
        return Atomic<T*>::get() != NULL;
    }

    bool operator !() const {
        return  Atomic<T*>::get() == NULL;
    }
};

class SpinLock {
public:
    SpinLock() : lock(0) {}

    bool tryAcquire() {
        return __sync_lock_test_and_set(&lock, 1) == 0;
    }

    void acquire() {
        while (!tryAcquire()) {
            sched_yield();
        }
    }

    void release() {
        __sync_lock_release(&lock);
    }

private:
    volatile int lock;
    DISALLOW_COPY_AND_ASSIGN(SpinLock);
};

class SpinLockHolder {
public:
    SpinLockHolder(SpinLock *theLock) : sl(theLock) {
        lock();
    }

    ~SpinLockHolder() {
        unlock();
    }

    void lock() {
        sl->acquire();
        locked = true;
    }

    void unlock() {
        if (locked) {
            sl->release();
            locked = false;
        }
    }
private:
    SpinLock *sl;
    bool locked;
};

template <class T> class RCPtr;

class RCValue {
public:
    RCValue() : _rc_refcount(0) {}
    RCValue(const RCValue &other) : _rc_refcount(0) {(void)other;}
    ~RCValue() {}
private:
    template <class TT> friend class RCPtr;
    int _rc_incref() const {
        return ++_rc_refcount;
    }

    int _rc_decref() const {
        return --_rc_refcount;
    }

    mutable Atomic<int> _rc_refcount;
};

template <class C>
class RCPtr {
public:
    RCPtr(C *init = NULL) : value(init) {
        if (init != NULL) {
            static_cast<RCValue*>(value)->_rc_incref();
        }
    }

    RCPtr(const RCPtr<C> &other) : value(other.gimme()) {}

    ~RCPtr() {
        if (value && static_cast<RCValue *>(value)->_rc_decref() == 0) {
            delete value;
        }
    }

    void reset(C *newValue = NULL) {
        if (newValue != NULL) {
            static_cast<RCValue *>(newValue)->_rc_incref();
        }
        swap(newValue);
    }

    void reset(const RCPtr<C> &other) {
        swap(other.gimme());
    }

    bool cas(RCPtr<C> &oldValue, RCPtr<C> &newValue) {
        SpinLockHolder lh(&lock);
        if (value == oldValue.get()) {
            C *tmp = value;
            value = newValue.gimme();
            if (tmp != NULL &&
                static_cast<RCValue *>(tmp)->_rc_decref() == 0) {
                lh.unlock();
                delete tmp;
            }
            return true;
        }
        return false;
    }

    // safe for the lifetime of this instance
    C *get() {
        return value;
    }

    void operator =(RCPtr<C> &other) {
        reset(other);
    }

    C &operator *() const {
        return *value;
    }

    C *operator ->() const {
        return value;
    }

    bool operator! () const {
        return !value;
    }

    operator bool () const {
        return (bool)value;
    }

private:
    C *gimme() const {
        SpinLockHolder lh(&lock);
        if (value) {
            static_cast<RCValue *>(value)->_rc_incref();
        }
        return value;
    }

    void swap(C *newValue) {
        SpinLockHolder lh(&lock);
        C *tmp(value.swap(newValue));
        lh.unlock();
        if (tmp != NULL && static_cast<RCValue *>(tmp)->_rc_decref() == 0) {
            delete tmp;
        }
    }

    AtomicPtr<C> value;
    mutable SpinLock lock; // exists solely for the purpose of implementing reset() safely
};

template <typename T>
class AtomicQueue {
public:
    AtomicQueue() : counter((size_t)0), numItems((size_t)0) {}

    ~AtomicQueue() {
        size_t i;
        for (i = 0; i < counter; ++i) {
            delete queues[i];
        }
    }

    void push(T value) {
        std::queue<T> *q = swapQueue(); // steal our queue
        q->push(value);
        ++numItems;
        q = swapQueue(q);
    }

    void pushQueue(std::queue<T> &inQueue) {
        std::queue<T> *q = swapQueue(); // steal our queue
        numItems.incr(inQueue.size());
        while (!inQueue.empty()) {
            q->push(inQueue.front());
            inQueue.pop();
        }
        q = swapQueue(q);
    }

    void getAll(std::queue<T> &outQueue) {
        std::queue<T> *q(swapQueue()); // Grab my own queue
        std::queue<T> *newQueue(NULL);
        int count(0);

        // Will start empty unless this thread is adding stuff
        while (!q->empty()) {
            outQueue.push(q->front());
            q->pop();
            ++count;
        }

        size_t c(counter);
        for (size_t i = 0; i < c; ++i) {
            // Swap with another thread
            newQueue = queues[i].swapIfNot(NULL, q);
            // Empty the queue
            if (newQueue != NULL) {
                q = newQueue;
                while (!q->empty()) {
                    outQueue.push(q->front());
                    q->pop();
                    ++count;
                }
            }
        }

        q = swapQueue(q);
        numItems -= count;
    }

    size_t getNumQueues() const {
        return counter;
    }

    bool empty() const {
        return size() == 0;
    }

    size_t size() const {
        return numItems;
    }
private:
    AtomicPtr<std::queue<T> > *initialize() {
        std::queue<T> *q = new std::queue<T>;
        size_t i(counter++);
        queues[i] = q;
        threadQueue = &queues[i];
        return &queues[i];
    }

    std::queue<T> *swapQueue(std::queue<T> *newQueue = NULL) {
        AtomicPtr<std::queue<T> > *qPtr(threadQueue);
        if (qPtr == NULL) {
            qPtr = initialize();
        }
        return qPtr->swap(newQueue);
    }

    ThreadLocalPtr<AtomicPtr<std::queue<T> > > threadQueue;
    AtomicPtr<std::queue<T> > queues[MAX_THREADS];
    Atomic<size_t> counter;
    Atomic<size_t> numItems;
    DISALLOW_COPY_AND_ASSIGN(AtomicQueue);
};

#endif // ATOMIC_HH
<|endoftext|>


<commit_before>#include "p0compile/parser.hpp"
#include "p0compile/expression_tree.hpp"
#include "p0compile/scanner.hpp"
#include "p0compile/compiler_error.hpp"
#include <boost/test/unit_test.hpp>

namespace
{
	bool handle_unexpected_error(p0::compiler_error const &error)
	{
		(void)error;
		BOOST_CHECK(nullptr == "No error expected");
		return true;
	}

	template <class ASTHandler>
	void test_parser(std::string const &source, ASTHandler const &handle_ast)
	{
		p0::source_range const source_range(
					source.data(),
					source.data() + source.size());
		p0::scanner scanner(source_range);
		p0::parser parser(scanner, handle_unexpected_error);
		auto const ast = parser.parse_unit();
		BOOST_REQUIRE(ast);
		handle_ast(*ast);
	}
}

BOOST_AUTO_TEST_CASE(parse_empty_file_test)
{
	test_parser("", [](p0::function_tree const &ast)
	{
		BOOST_CHECK(ast.parameters().empty());
		//TODO check empty body
	});
}
<commit_msg>test parse return<commit_after>#include "p0compile/parser.hpp"
#include "p0compile/expression_tree.hpp"
#include "p0compile/statement_tree.hpp"
#include "p0compile/scanner.hpp"
#include "p0compile/compiler_error.hpp"
#include <boost/test/unit_test.hpp>

namespace
{
	bool handle_unexpected_error(p0::compiler_error const &error)
	{
		(void)error;
		BOOST_CHECK(nullptr == "No error expected");
		return true;
	}

	template <class ASTHandler>
	void test_parser(std::string const &source, ASTHandler const &handle_ast)
	{
		p0::source_range const source_range(
					source.data(),
					source.data() + source.size());
		p0::scanner scanner(source_range);
		p0::parser parser(scanner, handle_unexpected_error);
		auto const ast = parser.parse_unit();
		BOOST_REQUIRE(ast);
		handle_ast(*ast);
	}

	template <class Base>
	struct down_caster
	{
		down_caster(Base const &base)
			: m_base(&base)
		{
		}

		template <class Down>
		operator Down const &() const
		{
			assert(m_base);
			return dynamic_cast<Down const &>(*m_base);
		}

	private:

		Base const *m_base;
	};

	template <class Handler>
	void check_expression(p0::expression_tree const &expression, Handler const &handler)
	{
		handler(down_caster<p0::expression_tree>(expression));
	}

	template <class Handler>
	void check_statement(p0::statement_tree const &statement, Handler const &handler)
	{
		handler(down_caster<p0::statement_tree>(statement));
	}
}

BOOST_AUTO_TEST_CASE(parse_empty_file_test)
{
	test_parser("", [](p0::function_tree const &ast)
	{
		BOOST_CHECK(ast.parameters().empty());
		check_statement(ast.body(), [](p0::block_tree const &block)
		{
			BOOST_CHECK(block.body().empty());
		});
	});
}

BOOST_AUTO_TEST_CASE(parse_return_test)
{
	test_parser("return null", [](p0::function_tree const &ast)
	{
		BOOST_CHECK(ast.parameters().empty());
		check_statement(ast.body(), [](p0::block_tree const &block)
		{
			BOOST_REQUIRE(block.body().size() == 1);
			check_statement(*block.body()[0], [](p0::return_tree const &return_)
			{
				check_expression(return_.value(), [](p0::null_expression_tree const &)
				{
				});
			});
		});
	});
}
<|endoftext|>


<commit_before>#ifndef ENTT_META_NODE_HPP
#define ENTT_META_NODE_HPP

#include <cstddef>
#include <memory>
#include <type_traits>
#include <utility>
#include "../config/config.h"
#include "../container/dense_map.hpp"
#include "../core/attribute.h"
#include "../core/enum.hpp"
#include "../core/fwd.hpp"
#include "../core/type_info.hpp"
#include "../core/type_traits.hpp"
#include "../core/utility.hpp"
#include "../locator/locator.hpp" // TODO
#include "context.hpp"
#include "type_traits.hpp"

namespace entt {

class meta_any;
class meta_type;
struct meta_handle;

/**
 * @cond TURN_OFF_DOXYGEN
 * Internal details not to be documented.
 */

namespace internal {

enum class meta_traits : std::uint32_t {
    is_none = 0x0000,
    is_const = 0x0001,
    is_static = 0x0002,
    is_arithmetic = 0x0004,
    is_integral = 0x0008,
    is_signed = 0x0010,
    is_array = 0x0020,
    is_enum = 0x0040,
    is_class = 0x0080,
    is_meta_pointer_like = 0x0100,
    is_meta_sequence_container = 0x0200,
    is_meta_associative_container = 0x0400,
    _entt_enum_as_bitmask
};

struct meta_type_node;

struct meta_prop_node {
    meta_type_node (*type)(const meta_context &) noexcept {};
    std::shared_ptr<void> value{};
};

struct meta_base_node {
    meta_type_node (*type)(const meta_context &) noexcept {};
    const void *(*cast)(const void *) noexcept {};
};

struct meta_conv_node {
    meta_any (*conv)(const meta_ctx &, const void *){};
};

struct meta_ctor_node {
    using size_type = std::size_t;

    size_type arity{0u};
    meta_type (*arg)(const meta_ctx &, const size_type) noexcept {};
    meta_any (*invoke)(const meta_ctx &, meta_any *const){};
};

struct meta_dtor_node {
    void (*dtor)(void *){};
};

struct meta_data_node {
    using size_type = std::size_t;

    meta_traits traits{meta_traits::is_none};
    size_type arity{0u};
    meta_type_node (*type)(const meta_context &) noexcept {};
    meta_type (*arg)(const meta_ctx &, const size_type) noexcept {};
    bool (*set)(const meta_ctx &, meta_handle, meta_any){};
    meta_any (*get)(const meta_ctx &, meta_handle){};
    dense_map<id_type, meta_prop_node, identity> prop{};
};

struct meta_func_node {
    using size_type = std::size_t;

    meta_traits traits{meta_traits::is_none};
    size_type arity{0u};
    meta_type_node (*ret)(const meta_context &) noexcept {};
    meta_type (*arg)(const meta_ctx &, const size_type) noexcept {};
    meta_any (*invoke)(const meta_ctx &, meta_handle, meta_any *const){};
    std::shared_ptr<meta_func_node> next{};
    dense_map<id_type, meta_prop_node, identity> prop{};
};

struct meta_template_node {
    using size_type = std::size_t;

    size_type arity{0u};
    meta_type_node (*type)(const meta_context &) noexcept {};
    meta_type_node (*arg)(const meta_context &, const size_type) noexcept {};
};

struct meta_type_descriptor {
    dense_map<id_type, meta_ctor_node, identity> ctor{};
    dense_map<id_type, meta_base_node, identity> base{};
    dense_map<id_type, meta_conv_node, identity> conv{};
    dense_map<id_type, meta_data_node, identity> data{};
    dense_map<id_type, meta_func_node, identity> func{};
    dense_map<id_type, meta_prop_node, identity> prop{};
};

struct meta_type_node {
    using size_type = std::size_t;

    const type_info *info{};
    id_type id{};
    meta_traits traits{meta_traits::is_none};
    size_type size_of{0u};
    meta_type_node (*remove_pointer)(const meta_context &) noexcept {};
    meta_any (*default_constructor)(const meta_ctx &){};
    double (*conversion_helper)(void *, const void *){};
    meta_any (*from_void)(const meta_ctx &, void *, const void *){};
    meta_template_node templ{};
    meta_dtor_node dtor{};
    std::shared_ptr<meta_type_descriptor> details{};
};

template<typename Type>
meta_type_node resolve(const meta_context &) noexcept;

template<typename Type>
[[nodiscard]] meta_type_node resolve_TODO() noexcept {
    return resolve<Type>(meta_context::from(locator<meta_ctx>::value_or()));
}

template<typename... Args>
[[nodiscard]] auto meta_arg_node(const meta_context &context, type_list<Args...>, [[maybe_unused]] const std::size_t index) noexcept {
    std::size_t pos{};
    meta_type_node (*value)(const meta_context &) noexcept = nullptr;
    ((value = (pos++ == index ? &resolve<std::remove_cv_t<std::remove_reference_t<Args>>> : value)), ...);
    ENTT_ASSERT(value != nullptr, "Out of bounds");
    return value(context);
}

[[nodiscard]] inline const void *try_cast(const meta_context &context, const meta_type_node &from, const meta_type_node &to, const void *instance) noexcept {
    if(from.info && to.info && *from.info == *to.info) {
        return instance;
    }

    if(from.details) {
        for(auto &&curr: from.details->base) {
            if(const void *elem = try_cast(context, curr.second.type(context), to, curr.second.cast(instance)); elem) {
                return elem;
            }
        }
    }

    return nullptr;
}

[[nodiscard]] inline const meta_type_node *try_resolve(const meta_context &context, const type_info &info) noexcept {
    const auto it = context.value.find(info.hash());
    return it != context.value.end() ? &it->second : nullptr;
}

template<typename Type>
void meta_default_constructor([[maybe_unused]] meta_type_node &node) {
    if constexpr(std::is_default_constructible_v<Type>) {
        node.default_constructor = +[](const meta_ctx &ctx) {
            return meta_any{ctx, std::in_place_type<Type>};
        };
    }
}

template<typename Type>
void meta_conversion_helper([[maybe_unused]] meta_type_node &node) {
    if constexpr(std::is_arithmetic_v<Type>) {
        node.conversion_helper = +[](void *bin, const void *value) {
            return bin ? static_cast<double>(*static_cast<Type *>(bin) = static_cast<Type>(*static_cast<const double *>(value))) : static_cast<double>(*static_cast<const Type *>(value));
        };
    } else if constexpr(std::is_enum_v<Type>) {
        node.conversion_helper = +[](void *bin, const void *value) {
            return bin ? static_cast<double>(*static_cast<Type *>(bin) = static_cast<Type>(static_cast<std::underlying_type_t<Type>>(*static_cast<const double *>(value)))) : static_cast<double>(*static_cast<const Type *>(value));
        };
    }
}

template<typename Type>
void meta_from_void([[maybe_unused]] meta_type_node &node) {
    if constexpr(!std::is_same_v<Type, void> && !std::is_function_v<Type>) {
        node.from_void = +[](const meta_ctx &ctx, void *element, const void *as_const) {
            if(element) {
                return meta_any{ctx, std::in_place_type<std::decay_t<Type> &>, *static_cast<std::decay_t<Type> *>(element)};
            }

            return meta_any{ctx, std::in_place_type<const std::decay_t<Type> &>, *static_cast<const std::decay_t<Type> *>(as_const)};
        };
    }
}

template<typename Type>
[[nodiscard]] meta_type_node resolve(const meta_context &context) noexcept {
    static_assert(std::is_same_v<Type, std::remove_const_t<std::remove_reference_t<Type>>>, "Invalid type");

    if(auto *elem = try_resolve(context, type_id<Type>()); elem) {
        return *elem;
    }

    meta_type_node node{
        &type_id<Type>(),
        type_id<Type>().hash(),
        (std::is_arithmetic_v<Type> ? meta_traits::is_arithmetic : meta_traits::is_none)
            | (std::is_integral_v<Type> ? meta_traits::is_integral : meta_traits::is_none)
            | (std::is_signed_v<Type> ? meta_traits::is_signed : meta_traits::is_none)
            | (std::is_array_v<Type> ? meta_traits::is_array : meta_traits::is_none)
            | (std::is_enum_v<Type> ? meta_traits::is_enum : meta_traits::is_none)
            | (std::is_class_v<Type> ? meta_traits::is_class : meta_traits::is_none)
            | (is_meta_pointer_like_v<Type> ? meta_traits::is_meta_pointer_like : meta_traits::is_none)
            | (is_complete_v<meta_sequence_container_traits<Type>> ? meta_traits::is_meta_sequence_container : meta_traits::is_none)
            | (is_complete_v<meta_associative_container_traits<Type>> ? meta_traits::is_meta_associative_container : meta_traits::is_none),
        size_of_v<Type>,
        &resolve<std::remove_cv_t<std::remove_pointer_t<Type>>>};

    meta_default_constructor<Type>(node);
    meta_conversion_helper<Type>(node);
    meta_from_void<Type>(node);

    if constexpr(is_complete_v<meta_template_traits<Type>>) {
        node.templ = meta_template_node{
            meta_template_traits<Type>::args_type::size,
            &resolve<typename meta_template_traits<Type>::class_type>,
            +[](const meta_context &area, const std::size_t index) noexcept { return meta_arg_node(area, typename meta_template_traits<Type>::args_type{}, index); }};
    }

    return node;
}

} // namespace internal

/**
 * Internal details not to be documented.
 * @endcond
 */

} // namespace entt

#endif
<commit_msg>meta: rollback redundant functions (reduce the number of generated symbols)<commit_after>#ifndef ENTT_META_NODE_HPP
#define ENTT_META_NODE_HPP

#include <cstddef>
#include <memory>
#include <type_traits>
#include <utility>
#include "../config/config.h"
#include "../container/dense_map.hpp"
#include "../core/attribute.h"
#include "../core/enum.hpp"
#include "../core/fwd.hpp"
#include "../core/type_info.hpp"
#include "../core/type_traits.hpp"
#include "../core/utility.hpp"
#include "../locator/locator.hpp" // TODO
#include "context.hpp"
#include "type_traits.hpp"

namespace entt {

class meta_any;
class meta_type;
struct meta_handle;

/**
 * @cond TURN_OFF_DOXYGEN
 * Internal details not to be documented.
 */

namespace internal {

enum class meta_traits : std::uint32_t {
    is_none = 0x0000,
    is_const = 0x0001,
    is_static = 0x0002,
    is_arithmetic = 0x0004,
    is_integral = 0x0008,
    is_signed = 0x0010,
    is_array = 0x0020,
    is_enum = 0x0040,
    is_class = 0x0080,
    is_meta_pointer_like = 0x0100,
    is_meta_sequence_container = 0x0200,
    is_meta_associative_container = 0x0400,
    _entt_enum_as_bitmask
};

struct meta_type_node;

struct meta_prop_node {
    meta_type_node (*type)(const meta_context &) noexcept {};
    std::shared_ptr<void> value{};
};

struct meta_base_node {
    meta_type_node (*type)(const meta_context &) noexcept {};
    const void *(*cast)(const void *) noexcept {};
};

struct meta_conv_node {
    meta_any (*conv)(const meta_ctx &, const void *){};
};

struct meta_ctor_node {
    using size_type = std::size_t;

    size_type arity{0u};
    meta_type (*arg)(const meta_ctx &, const size_type) noexcept {};
    meta_any (*invoke)(const meta_ctx &, meta_any *const){};
};

struct meta_dtor_node {
    void (*dtor)(void *){};
};

struct meta_data_node {
    using size_type = std::size_t;

    meta_traits traits{meta_traits::is_none};
    size_type arity{0u};
    meta_type_node (*type)(const meta_context &) noexcept {};
    meta_type (*arg)(const meta_ctx &, const size_type) noexcept {};
    bool (*set)(const meta_ctx &, meta_handle, meta_any){};
    meta_any (*get)(const meta_ctx &, meta_handle){};
    dense_map<id_type, meta_prop_node, identity> prop{};
};

struct meta_func_node {
    using size_type = std::size_t;

    meta_traits traits{meta_traits::is_none};
    size_type arity{0u};
    meta_type_node (*ret)(const meta_context &) noexcept {};
    meta_type (*arg)(const meta_ctx &, const size_type) noexcept {};
    meta_any (*invoke)(const meta_ctx &, meta_handle, meta_any *const){};
    std::shared_ptr<meta_func_node> next{};
    dense_map<id_type, meta_prop_node, identity> prop{};
};

struct meta_template_node {
    using size_type = std::size_t;

    size_type arity{0u};
    meta_type_node (*type)(const meta_context &) noexcept {};
    meta_type_node (*arg)(const meta_context &, const size_type) noexcept {};
};

struct meta_type_descriptor {
    dense_map<id_type, meta_ctor_node, identity> ctor{};
    dense_map<id_type, meta_base_node, identity> base{};
    dense_map<id_type, meta_conv_node, identity> conv{};
    dense_map<id_type, meta_data_node, identity> data{};
    dense_map<id_type, meta_func_node, identity> func{};
    dense_map<id_type, meta_prop_node, identity> prop{};
};

struct meta_type_node {
    using size_type = std::size_t;

    const type_info *info{};
    id_type id{};
    meta_traits traits{meta_traits::is_none};
    size_type size_of{0u};
    meta_type_node (*remove_pointer)(const meta_context &) noexcept {};
    meta_any (*default_constructor)(const meta_ctx &){};
    double (*conversion_helper)(void *, const void *){};
    meta_any (*from_void)(const meta_ctx &, void *, const void *){};
    meta_template_node templ{};
    meta_dtor_node dtor{};
    std::shared_ptr<meta_type_descriptor> details{};
};

template<typename Type>
meta_type_node resolve(const meta_context &) noexcept;

template<typename Type>
[[nodiscard]] meta_type_node resolve_TODO() noexcept {
    return resolve<Type>(meta_context::from(locator<meta_ctx>::value_or()));
}

template<typename... Args>
[[nodiscard]] auto meta_arg_node(const meta_context &context, type_list<Args...>, [[maybe_unused]] const std::size_t index) noexcept {
    std::size_t pos{};
    meta_type_node (*value)(const meta_context &) noexcept = nullptr;
    ((value = (pos++ == index ? &resolve<std::remove_cv_t<std::remove_reference_t<Args>>> : value)), ...);
    ENTT_ASSERT(value != nullptr, "Out of bounds");
    return value(context);
}

[[nodiscard]] inline const void *try_cast(const meta_context &context, const meta_type_node &from, const meta_type_node &to, const void *instance) noexcept {
    if(from.info && to.info && *from.info == *to.info) {
        return instance;
    }

    if(from.details) {
        for(auto &&curr: from.details->base) {
            if(const void *elem = try_cast(context, curr.second.type(context), to, curr.second.cast(instance)); elem) {
                return elem;
            }
        }
    }

    return nullptr;
}

[[nodiscard]] inline const meta_type_node *try_resolve(const meta_context &context, const type_info &info) noexcept {
    const auto it = context.value.find(info.hash());
    return it != context.value.end() ? &it->second : nullptr;
}

template<typename Type>
[[nodiscard]] meta_type_node resolve(const meta_context &context) noexcept {
    static_assert(std::is_same_v<Type, std::remove_const_t<std::remove_reference_t<Type>>>, "Invalid type");

    if(auto *elem = try_resolve(context, type_id<Type>()); elem) {
        return *elem;
    }

    meta_type_node node{
        &type_id<Type>(),
        type_id<Type>().hash(),
        (std::is_arithmetic_v<Type> ? meta_traits::is_arithmetic : meta_traits::is_none)
            | (std::is_integral_v<Type> ? meta_traits::is_integral : meta_traits::is_none)
            | (std::is_signed_v<Type> ? meta_traits::is_signed : meta_traits::is_none)
            | (std::is_array_v<Type> ? meta_traits::is_array : meta_traits::is_none)
            | (std::is_enum_v<Type> ? meta_traits::is_enum : meta_traits::is_none)
            | (std::is_class_v<Type> ? meta_traits::is_class : meta_traits::is_none)
            | (is_meta_pointer_like_v<Type> ? meta_traits::is_meta_pointer_like : meta_traits::is_none)
            | (is_complete_v<meta_sequence_container_traits<Type>> ? meta_traits::is_meta_sequence_container : meta_traits::is_none)
            | (is_complete_v<meta_associative_container_traits<Type>> ? meta_traits::is_meta_associative_container : meta_traits::is_none),
        size_of_v<Type>,
        &resolve<std::remove_cv_t<std::remove_pointer_t<Type>>>};

    if constexpr(std::is_default_constructible_v<Type>) {
        node.default_constructor = +[](const meta_ctx &ctx) {
            return meta_any{ctx, std::in_place_type<Type>};
        };
    }

    if constexpr(std::is_arithmetic_v<Type>) {
        node.conversion_helper = +[](void *bin, const void *value) {
            return bin ? static_cast<double>(*static_cast<Type *>(bin) = static_cast<Type>(*static_cast<const double *>(value))) : static_cast<double>(*static_cast<const Type *>(value));
        };
    } else if constexpr(std::is_enum_v<Type>) {
        node.conversion_helper = +[](void *bin, const void *value) {
            return bin ? static_cast<double>(*static_cast<Type *>(bin) = static_cast<Type>(static_cast<std::underlying_type_t<Type>>(*static_cast<const double *>(value)))) : static_cast<double>(*static_cast<const Type *>(value));
        };
    }

    if constexpr(!std::is_same_v<Type, void> && !std::is_function_v<Type>) {
        node.from_void = +[](const meta_ctx &ctx, void *element, const void *as_const) {
            if(element) {
                return meta_any{ctx, std::in_place_type<std::decay_t<Type> &>, *static_cast<std::decay_t<Type> *>(element)};
            }

            return meta_any{ctx, std::in_place_type<const std::decay_t<Type> &>, *static_cast<const std::decay_t<Type> *>(as_const)};
        };
    }

    if constexpr(is_complete_v<meta_template_traits<Type>>) {
        node.templ = meta_template_node{
            meta_template_traits<Type>::args_type::size,
            &resolve<typename meta_template_traits<Type>::class_type>,
            +[](const meta_context &area, const std::size_t index) noexcept { return meta_arg_node(area, typename meta_template_traits<Type>::args_type{}, index); }};
    }

    return node;
}

} // namespace internal

/**
 * Internal details not to be documented.
 * @endcond
 */

} // namespace entt

#endif
<|endoftext|>


<commit_before>#ifdef GRAVITY

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<math.h>
#include"../global.h"
#include "../io.h"

#include"grav3D.h"

#ifdef PARALLEL_OMP
#include "../parallel_omp.h"
#endif

Grav3D::Grav3D( void ){}

void Grav3D::Initialize( Real x_min, Real y_min, Real z_min, Real Lx, Real Ly, Real Lz, int nx, int ny, int nz, int nx_real, int ny_real, int nz_real, Real dx_real, Real dy_real, Real dz_real, int n_ghost_pot_offset, struct parameters *P )
{

  //Set Box Size
  Lbox_x = Lx;
  Lbox_y = Ly;
  Lbox_z = Lz;

  //Set Box Left boundary positions
  xMin = x_min;
  yMin = y_min;
  zMin = z_min;

  //Set uniform ( dx, dy, dz )
  dx = dx_real;
  dy = dy_real;
  dz = dz_real;

  //Set Box Total number of cells
  nx_total = nx;
  ny_total = ny;
  nz_total = nz;

  //Set Box local domain number of cells
  nx_local = nx_real;
  ny_local = ny_real;
  nz_local = nz_real;

  //Local n_cells without ghost cells
  n_cells = nx_local*ny_local*nz_local;
  //Local n_cells including ghost cells for the potential array
  n_cells_potential = ( nx_local + 2*N_GHOST_POTENTIAL ) * ( ny_local + 2*N_GHOST_POTENTIAL ) * ( nz_local + 2*N_GHOST_POTENTIAL );

  //Set Initial and dt used for the extrapolation of the potential;
  //The first timestep the potetential in not extrapolated ( INITIAL = TRUE )
  INITIAL = true;
  dt_prev = 0;
  dt_now = 0;

  #ifdef COSMOLOGY
  //Set the scale factor for cosmological simulations to 1,
  //This will be changed to the proper value when cosmology is initialized
  current_a = 1;
  #endif

  //Set the average density=0 ( Not Used )
  dens_avrg = 0;

  //Set the Gravitational Constant ( units must be consistent )
  Gconst = GN;
  if (strcmp(P->init, "Spherical_Overdensity_3D")==0){
    Gconst = 1;
    chprintf(" WARNING: Using Gravitational Constant G=1.\n");
  }

  //Flag to transfer the Potential boundaries
  TRANSFER_POTENTIAL_BOUNDARIES = false;

  // Flag to set the gravity boundariy flags
  BC_FLAGS_SET = false;

  AllocateMemory_CPU();

  #ifdef GRAVITY_GPU;
  AllocateMemory_GPU();
  #endif

  Initialize_values_CPU();

  chprintf( "Gravity Initialized: \n Lbox: %0.2f %0.2f %0.2f \n Local: %d %d %d \n Global: %d %d %d \n",
      Lbox_x, Lbox_y, Lbox_z, nx_local, ny_local, nz_local,   nx_total, ny_total, nz_total );

  chprintf( " dx:%f  dy:%f  dz:%f\n", dx, dy, dz );
  chprintf( " N ghost potential: %d\n", N_GHOST_POTENTIAL);
  chprintf( " N ghost offset: %d\n", n_ghost_pot_offset);

  #ifdef PARALLEL_OMP
  chprintf(" Using OMP for gravity calculations\n");
  int n_omp_max = omp_get_max_threads();
  chprintf("  MAX OMP Threads: %d\n", n_omp_max);
  chprintf("  N OMP Threads per MPI process: %d\n", N_OMP_THREADS);
  #endif

#ifdef PARIS
  const bool periodic = (P->xlg_bcnd != 3);
#ifdef PARIS_TEST
  Poisson_solver.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz );
  Poisson_solver_test.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz, periodic );
#else
  Poisson_solver.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz, periodic );
#endif
#else
  Poisson_solver.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz );
#endif
}

void Grav3D::AllocateMemory_CPU(void)
{
  // allocate memory for the density and potential arrays
  F.density_h    = (Real *) malloc(n_cells*sizeof(Real)); //array for the density
  F.potential_h  = (Real *) malloc(n_cells_potential*sizeof(Real));   //array for the potential at the n-th timestep
  F.potential_1_h  = (Real *) malloc(n_cells_potential*sizeof(Real)); //array for the potential at the (n-1)-th timestep
  boundary_flags = (int *) malloc(6*sizeof(int)); // array for the gtravity boundary flags

  #ifdef GRAV_ISOLATED_BOUNDARY_X
  F.pot_boundary_x0  = (Real *) malloc(N_GHOST_POTENTIAL*ny_local*nz_local*sizeof(Real)); //array for the potential isolated boundary
  F.pot_boundary_x1  = (Real *) malloc(N_GHOST_POTENTIAL*ny_local*nz_local*sizeof(Real));
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Y
  F.pot_boundary_y0  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*nz_local*sizeof(Real)); //array for the potential isolated boundary
  F.pot_boundary_y1  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*nz_local*sizeof(Real));
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Z
  F.pot_boundary_z0  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*ny_local*sizeof(Real)); //array for the potential isolated boundary
  F.pot_boundary_z1  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*ny_local*sizeof(Real));
  #endif
}

void Grav3D::Set_Boundary_Flags( int *flags ){
  for (int i=0; i<6; i++) boundary_flags[i] = flags[i];
}

void Grav3D::Initialize_values_CPU(void){

  //Set initial values to 0.
  for (int id=0; id<n_cells; id++){
    F.density_h[id] = 0;
  }

  for (int id_pot=0; id_pot<n_cells_potential; id_pot++){
    F.potential_h[id_pot] = 0;
    F.potential_1_h[id_pot] = 0;
  }
}

void Grav3D::FreeMemory_CPU(void)
{
  free(F.density_h);
  free(F.potential_h);
  free(F.potential_1_h);
  free( boundary_flags );

  #ifdef GRAV_ISOLATED_BOUNDARY_X
  free(F.pot_boundary_x0);
  free(F.pot_boundary_x1);
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Y
  free(F.pot_boundary_y0);
  free(F.pot_boundary_y1);
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Z
  free(F.pot_boundary_z0);
  free(F.pot_boundary_z1);
  #endif

  Poisson_solver.Reset();
  #ifdef PARIS_TEST
  Poisson_solver_test.Reset();
  #endif
}

#endif //GRAVITY
<commit_msg>fixed bug on GRAVITY_GPU compiler flag<commit_after>#ifdef GRAVITY

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<math.h>
#include"../global.h"
#include "../io.h"

#include"grav3D.h"

#ifdef PARALLEL_OMP
#include "../parallel_omp.h"
#endif

Grav3D::Grav3D( void ){}

void Grav3D::Initialize( Real x_min, Real y_min, Real z_min, Real Lx, Real Ly, Real Lz, int nx, int ny, int nz, int nx_real, int ny_real, int nz_real, Real dx_real, Real dy_real, Real dz_real, int n_ghost_pot_offset, struct parameters *P )
{

  //Set Box Size
  Lbox_x = Lx;
  Lbox_y = Ly;
  Lbox_z = Lz;

  //Set Box Left boundary positions
  xMin = x_min;
  yMin = y_min;
  zMin = z_min;

  //Set uniform ( dx, dy, dz )
  dx = dx_real;
  dy = dy_real;
  dz = dz_real;

  //Set Box Total number of cells
  nx_total = nx;
  ny_total = ny;
  nz_total = nz;

  //Set Box local domain number of cells
  nx_local = nx_real;
  ny_local = ny_real;
  nz_local = nz_real;

  //Local n_cells without ghost cells
  n_cells = nx_local*ny_local*nz_local;
  //Local n_cells including ghost cells for the potential array
  n_cells_potential = ( nx_local + 2*N_GHOST_POTENTIAL ) * ( ny_local + 2*N_GHOST_POTENTIAL ) * ( nz_local + 2*N_GHOST_POTENTIAL );

  //Set Initial and dt used for the extrapolation of the potential;
  //The first timestep the potetential in not extrapolated ( INITIAL = TRUE )
  INITIAL = true;
  dt_prev = 0;
  dt_now = 0;

  #ifdef COSMOLOGY
  //Set the scale factor for cosmological simulations to 1,
  //This will be changed to the proper value when cosmology is initialized
  current_a = 1;
  #endif

  //Set the average density=0 ( Not Used )
  dens_avrg = 0;

  //Set the Gravitational Constant ( units must be consistent )
  Gconst = GN;
  if (strcmp(P->init, "Spherical_Overdensity_3D")==0){
    Gconst = 1;
    chprintf(" WARNING: Using Gravitational Constant G=1.\n");
  }

  //Flag to transfer the Potential boundaries
  TRANSFER_POTENTIAL_BOUNDARIES = false;

  // Flag to set the gravity boundariy flags
  BC_FLAGS_SET = false;

  AllocateMemory_CPU();

  #ifdef GRAVITY_GPU
  AllocateMemory_GPU();
  #endif

  Initialize_values_CPU();

  chprintf( "Gravity Initialized: \n Lbox: %0.2f %0.2f %0.2f \n Local: %d %d %d \n Global: %d %d %d \n",
      Lbox_x, Lbox_y, Lbox_z, nx_local, ny_local, nz_local,   nx_total, ny_total, nz_total );

  chprintf( " dx:%f  dy:%f  dz:%f\n", dx, dy, dz );
  chprintf( " N ghost potential: %d\n", N_GHOST_POTENTIAL);
  chprintf( " N ghost offset: %d\n", n_ghost_pot_offset);

  #ifdef PARALLEL_OMP
  chprintf(" Using OMP for gravity calculations\n");
  int n_omp_max = omp_get_max_threads();
  chprintf("  MAX OMP Threads: %d\n", n_omp_max);
  chprintf("  N OMP Threads per MPI process: %d\n", N_OMP_THREADS);
  #endif

#ifdef PARIS
  const bool periodic = (P->xlg_bcnd != 3);
#ifdef PARIS_TEST
  Poisson_solver.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz );
  Poisson_solver_test.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz, periodic );
#else
  Poisson_solver.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz, periodic );
#endif
#else
  Poisson_solver.Initialize( Lbox_x, Lbox_y, Lbox_z, xMin, yMin, zMin, nx_total, ny_total, nz_total, nx_local, ny_local, nz_local, dx, dy, dz );
#endif
}

void Grav3D::AllocateMemory_CPU(void)
{
  // allocate memory for the density and potential arrays
  F.density_h    = (Real *) malloc(n_cells*sizeof(Real)); //array for the density
  F.potential_h  = (Real *) malloc(n_cells_potential*sizeof(Real));   //array for the potential at the n-th timestep
  F.potential_1_h  = (Real *) malloc(n_cells_potential*sizeof(Real)); //array for the potential at the (n-1)-th timestep
  boundary_flags = (int *) malloc(6*sizeof(int)); // array for the gtravity boundary flags

  #ifdef GRAV_ISOLATED_BOUNDARY_X
  F.pot_boundary_x0  = (Real *) malloc(N_GHOST_POTENTIAL*ny_local*nz_local*sizeof(Real)); //array for the potential isolated boundary
  F.pot_boundary_x1  = (Real *) malloc(N_GHOST_POTENTIAL*ny_local*nz_local*sizeof(Real));
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Y
  F.pot_boundary_y0  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*nz_local*sizeof(Real)); //array for the potential isolated boundary
  F.pot_boundary_y1  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*nz_local*sizeof(Real));
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Z
  F.pot_boundary_z0  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*ny_local*sizeof(Real)); //array for the potential isolated boundary
  F.pot_boundary_z1  = (Real *) malloc(N_GHOST_POTENTIAL*nx_local*ny_local*sizeof(Real));
  #endif
}

void Grav3D::Set_Boundary_Flags( int *flags ){
  for (int i=0; i<6; i++) boundary_flags[i] = flags[i];
}

void Grav3D::Initialize_values_CPU(void){

  //Set initial values to 0.
  for (int id=0; id<n_cells; id++){
    F.density_h[id] = 0;
  }

  for (int id_pot=0; id_pot<n_cells_potential; id_pot++){
    F.potential_h[id_pot] = 0;
    F.potential_1_h[id_pot] = 0;
  }
}

void Grav3D::FreeMemory_CPU(void)
{
  free(F.density_h);
  free(F.potential_h);
  free(F.potential_1_h);
  free( boundary_flags );

  #ifdef GRAV_ISOLATED_BOUNDARY_X
  free(F.pot_boundary_x0);
  free(F.pot_boundary_x1);
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Y
  free(F.pot_boundary_y0);
  free(F.pot_boundary_y1);
  #endif
  #ifdef GRAV_ISOLATED_BOUNDARY_Z
  free(F.pot_boundary_z0);
  free(F.pot_boundary_z1);
  #endif

  Poisson_solver.Reset();
  #ifdef PARIS_TEST
  Poisson_solver_test.Reset();
  #endif
}

#endif //GRAVITY
<|endoftext|>


<commit_before>/*
 * Copyright (C) 2014-2015 Pavel Dolgov
 *
 * See the LICENSE file for terms of use.
 */

#include "TableModel.hpp"

typedef QModelIndex Index;

TableModel::TableModel(QObject* parent,
                       const GameDesk* desk):
    QAbstractTableModel(parent), desk_(desk) {
}

int TableModel::rowCount(const Index& /*parent*/) const {
    return desk_->getRowNumber();
}

int TableModel::columnCount(
    const Index& /*parent*/) const {
    return desk_->getRowNumber();
}

QVariant TableModel::data(const Index& index,
                          int role) const {
    if (role == Qt::DisplayRole) {
        int desk_size = desk_->getRowNumber();
        Point pt = getModelIndex(index, desk_size);
        return desk_->getDeskNumber(pt);
    }
    return QVariant();
}

void TableModel::updateData() {
    reset();
}
<commit_msg>GUI: center all the numbers in cells of game board<commit_after>/*
 * Copyright (C) 2014-2015 Pavel Dolgov
 *
 * See the LICENSE file for terms of use.
 */

#include "TableModel.hpp"

typedef QModelIndex Index;

TableModel::TableModel(QObject* parent,
                       const GameDesk* desk):
    QAbstractTableModel(parent), desk_(desk) {
}

int TableModel::rowCount(const Index& /*parent*/) const {
    return desk_->getRowNumber();
}

int TableModel::columnCount(
    const Index& /*parent*/) const {
    return desk_->getRowNumber();
}

QVariant TableModel::data(const Index& index,
                          int role) const {
    if (role == Qt::DisplayRole) {
        int desk_size = desk_->getRowNumber();
        Point pt = getModelIndex(index, desk_size);
        return desk_->getDeskNumber(pt);
    } else if (role == Qt::TextAlignmentRole) {
        return Qt::AlignCenter;
    }
    return QVariant();
}

void TableModel::updateData() {
    reset();
}
<|endoftext|>


<commit_before>/*
	This file is part of the CVD Library.

	Copyright (C) 2005 The Authors

	This library is free software; you can redistribute it and/or
	modify it under the terms of the GNU Lesser General Public
	License as published by the Free Software Foundation; either
	version 2.1 of the License, or (at your option) any later version.

	This library is distributed in the hope that it will be useful,
	but WITHOUT ANY WARRANTY; without even the implied warranty of
	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
	Lesser General Public License for more details.

	You should have received a copy of the GNU Lesser General Public
	License along with this library; if not, write to the Free Software
	Foundation, Inc.,
    51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
*/
#include "pnm_src/save_postscript.h"

#include "cvd/image_io.h"
#include <iostream>
#include <string>
#include <iomanip>
using namespace std;

namespace CVD
{

void output_eps_header(ostream& o, int xs, int ys)
{
	o <<
	"%!PS-Adobe-3.0 EPSF-3.0"																"\n"
	"%%BoundingBox: 0 0 " << xs << " " << ys << 											"\n"
	"%%Creator: libCVD"																		"\n"
	"%%Pages: 0"																			"\n"
	"%%EndComments"																			"\n"
	"%%EndProlog"																			"\n"
	"save"																					"\n"
	"20 dict begin"																			"\n";
}

void output_eps_header(ostream& o, const ImageRef& s)
{
	output_eps_header(o, s.x, s.y);
}

void output_eps_footer(ostream& o)
{
	o << "end restore\n"
	  << "%%EOF\n";
}

namespace PNM
{

string ps_out::bytes_to_base85(int n)
{
	//This function converts 4 raw bytes to 5 base-85 bytes. If there
	//are less than 4 bytes, then the datat is zero padded.

	//Conversion to base85 is done the obvious way, but 33 is added
	//to each number to make it a printable byte.

	//There is a shortcut which means that !!!!! is abbreviated as z

	unsigned long int num = 0;

	for(int i=0; i <n; i++)
		num |= buf[i] << ((3-i) * 8);

	if(num == 0)
		return "z";

	string r;
	r.resize(5);

	for(int i=0; i < 5; i++)
	{
		r[4-i] = num % 85 + 33;
		num /= 85;
	}

	return r;
}

void ps_out::output_header()
{
	//Output the required instructions. This sets up a 72 dpi image, the ``right'' way up,
	//going from 0,0 - xs, ys. Since numbers are 72 per inch, the image is 72 dpi
	o << " 0 " << ys << " translate 1 -1 scale " << xs << " " << ys << " 8 matrix  currentfile\n"
		" /ASCII85Decode filter false " << m_channels << " colorimage\n";
}

ps_out::ps_out(std::ostream& out)
:o(out)
{
	num_in_buf = lines = 0;
}

ps_out::ps_out(std::ostream& out, int xsize, int ysize, int try_channels, bool use2bytes, const string& comm)
:o(out)
{
	xs = xsize;
	ys = ysize;
	num_in_buf = lines = 0;

	m_is_2_byte = 0;

	if(try_channels < 3)
		m_channels = 1;
	else
		m_channels = 3;

	output_header();

}

ps_out::~ps_out()
{
}

void ps_out::write_raw_pixel_lines(const unsigned short* data, unsigned long nlines)
{
	throw CVD::Exceptions::Image_IO::WriteError("Postscript: Internal error: can not write 16bit Postscript image.");
}

void ps_out::write_raw_pixel_lines(const unsigned char* data, unsigned long nlines)
{
	if(nlines + lines > ys)
		throw CVD::Exceptions::Image_IO::WriteError("Postscript: Internal error: attempting to write too many lines.");

	const unsigned char* end = data + (nlines * xs)*m_channels;
	const unsigned char* d = data;

	string currentline;
	currentline.reserve(80);

	while(d < end)
	{
		//Stuff 4 bytes in to the buffer
		for(; num_in_buf < 4 && d < end; num_in_buf++, d++)
			buf[num_in_buf] = *d;

		//Append the base-85 encoded bytes
		currentline += bytes_to_base85(num_in_buf);
		num_in_buf = 0;

		//Output the line of it is wide enough
		if(currentline.size() >= 75)
		{
			o << currentline << endl;
			currentline.resize(0);
		}
	}

	//Output if there is anything left
	if(currentline.size())
		o << currentline << endl;

	lines += nlines;

	//Delimit the data
	if(lines == ys)
		o << "~>\n";
}

eps_out::eps_out(std::ostream& out, int xsize, int ysize, int try_channels, bool use2bytes, const string& comm)
:ps_out(out)
{
	xs = xsize;
	ys = ysize;

	m_is_2_byte = 0;

	if(try_channels < 3)
		m_channels = 1;
	else
		m_channels = 3;

	output_eps_header(o, xs, ys);
	output_header();

}

eps_out::~eps_out()
{
	output_eps_footer(o);
}

}
}
<commit_msg>Added comments about saving to PS.<commit_after>/*
	This file is part of the CVD Library.

	Copyright (C) 2005 The Authors

	This library is free software; you can redistribute it and/or
	modify it under the terms of the GNU Lesser General Public
	License as published by the Free Software Foundation; either
	version 2.1 of the License, or (at your option) any later version.

	This library is distributed in the hope that it will be useful,
	but WITHOUT ANY WARRANTY; without even the implied warranty of
	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
	Lesser General Public License for more details.

	You should have received a copy of the GNU Lesser General Public
	License along with this library; if not, write to the Free Software
	Foundation, Inc.,
    51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
*/
#include "pnm_src/save_postscript.h"

#include "cvd/image_io.h"
#include <iostream>
#include <string>
#include <iomanip>
using namespace std;

namespace CVD
{

void output_eps_header(ostream& o, int xs, int ys)
{
	//Standard EPS header. This is test more by concensus from various postscript handlers
	//than with any specific reference to documentation, but it seems to work.
	o <<
	"%!PS-Adobe-3.0 EPSF-3.0"																"\n"
	"%%BoundingBox: 0 0 " << xs << " " << ys << 											"\n"
	"%%Creator: libCVD"																		"\n"
	"%%Pages: 0"																			"\n"
	"%%EndComments"																			"\n"
	"%%EndProlog"																			"\n"
	//This saves the dictionary state and enables a temporary dictionary.
	//this should prevent the eps file from polluting the vm or dictionary.
	//it's kind of the job of whatever includes EPS to do this, but this makes
	//the job easier and improves reliability. Note that in Level 2 ps, the
	//dictionary can expand if more than 20 commands are added later.
	//If custom PS is added, it must leave the stack empty at the end.
	"save"																					"\n"
	"20 dict begin"																			"\n";
}

void output_eps_header(ostream& o, const ImageRef& s)
{
	output_eps_header(o, s.x, s.y);
}

void output_eps_footer(ostream& o)
{
	//End the temporary dictionary and restore the VM and graphics state.
	o << "end restore\n"
	//I'm not sure exactly what the end of an EPS image should be, but this
	//seems to work.
	  << "%%EOF\n";
}

namespace PNM
{

string ps_out::bytes_to_base85(int n)
{
	//This function converts 4 raw bytes to 5 base-85 bytes. If there
	//are less than 4 bytes, then the data is zero padded.

	//Conversion to base85 is done the obvious way, but 33 is added
	//to each number to make it a printable byte.

	//There is a shortcut which means that !!!!! is abbreviated as z

	unsigned long int num = 0;

	for(int i=0; i <n; i++)
		num |= buf[i] << ((3-i) * 8);

	if(num == 0)
		return "z";

	string r;
	r.resize(5);

	for(int i=0; i < 5; i++)
	{
		r[4-i] = num % 85 + 33;
		num /= 85;
	}

	return r;
}

void ps_out::output_header()
{
	//Output the required instructions. This sets up a 72 dpi image, the ``right'' way up,
	//going from 0,0 - xs, ys. Since numbers are 72 per inch, the image is 72 dpi
	o << " 0 " << ys << " translate 1 -1 scale " << xs << " " << ys << " 8 matrix  currentfile\n"
		" /ASCII85Decode filter false " << m_channels << " colorimage\n";

	// <xsize> <ysize> <bits per channel> <transform> <datasrc n> ... <datasrc 1> <multi> <num of channels> colorimage
	// transform is an affine transformation matrix. We use the identity here,
	// and preform the the transform before the image, so that any subsequent
	// graphics appear in the coordinate frame of the image.

}

ps_out::ps_out(std::ostream& out)
:o(out)
{
	num_in_buf = lines = 0;
}

ps_out::ps_out(std::ostream& out, int xsize, int ysize, int try_channels, bool use2bytes, const string& comm)
:o(out)
{
	xs = xsize;
	ys = ysize;
	num_in_buf = lines = 0;

	m_is_2_byte = 0;

	if(try_channels < 3)
		m_channels = 1;
	else
		m_channels = 3;

	output_header();

}

ps_out::~ps_out()
{
}

void ps_out::write_raw_pixel_lines(const unsigned short* data, unsigned long nlines)
{
	//I think PS supports 12 bit images. They could be supported here.
	throw CVD::Exceptions::Image_IO::WriteError("Postscript: Internal error: can not write 16bit Postscript image.");
}

void ps_out::write_raw_pixel_lines(const unsigned char* data, unsigned long nlines)
{
	if(nlines + lines > ys)
		throw CVD::Exceptions::Image_IO::WriteError("Postscript: Internal error: attempting to write too many lines.");

	const unsigned char* end = data + (nlines * xs)*m_channels;
	const unsigned char* d = data;

	string currentline;
	currentline.reserve(80);

	while(d < end)
	{
		//Stuff 4 bytes in to the buffer
		for(; num_in_buf < 4 && d < end; num_in_buf++, d++)
			buf[num_in_buf] = *d;

		//Append the base-85 encoded bytes
		currentline += bytes_to_base85(num_in_buf);
		num_in_buf = 0;

		//Output the line of it is wide enough
		if(currentline.size() >= 75)
		{
			o << currentline << endl;
			currentline.resize(0);
		}
	}

	//Output if there is anything left
	if(currentline.size())
		o << currentline << endl;

	lines += nlines;

	//Delimit the data
	if(lines == ys)
		o << "~>\n";
}

eps_out::eps_out(std::ostream& out, int xsize, int ysize, int try_channels, bool use2bytes, const string& comm)
:ps_out(out)
{
	xs = xsize;
	ys = ysize;

	m_is_2_byte = 0;

	if(try_channels < 3)
		m_channels = 1;
	else
		m_channels = 3;

	output_eps_header(o, xs, ys);
	output_header();

}

eps_out::~eps_out()
{
	output_eps_footer(o);
}

}
}
<|endoftext|>


<commit_before>// Copyright (c) 2013 Joshua Beitler, Mirus contributors

// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.

#ifndef _MIRUS_KERNEL_MX_H_
#define _MIRUS_KERNEL_MX_H_

namespace mirus
{
    // defines flags for the "flags" variable in the header
    enum class mx_flags
    {

    };

    // defines mx versions
    enum class mx_version : unsigned char
    {
        MX_0,       // MX 0 = development version
        MX_1        // MX 1 = first version
    };

    // defines a mirus executable file header
    class mx_header
    {
    public:
        unsigned char       magicnumber;
        mx_version          version;
        unsigned char       flags;

        unsigned short      section_start_data;
        unsigned short      section_start_bss;
        unsigned short      section_start_text;
    };

    // defines a mirus executable
    class mx
    {
    public:
        mx_header header;
    };
}

#endif
<commit_msg>Added additional header fields<commit_after>// Copyright (c) 2013 Joshua Beitler, Mirus contributors

// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.

#ifndef _MIRUS_KERNEL_MX_H_
#define _MIRUS_KERNEL_MX_H_

namespace mirus
{
    // defines flags for the "flags" variable in the header
    enum class mx_flags : int
    {
        PLATFORM_AMD_ONLY    // AMD x64 only
    };

    // defines mx versions
    enum class mx_version : unsigned char
    {
        MX_0,               // MX 0 = development version
        MX_1                // MX 1 = first version
    };

    // defines a mirus executable file header
    class mx_header
    {
    public:
        // basic executable stuff
        unsigned char       magicnumber;
        mx_version          version;
        unsigned char       flags;

        // where do the sections start
        unsigned short      section_start_data;
        unsigned short      section_start_bss;
        unsigned short      section_start_text;

        // misc information about the app
        char*               program_name;
        char*               developer;

        // app version - we try to follow semver (semver.org)
        int                 version_major;
        int                 version_minor;
        int                 version_rev;
        int                 version_build;
    };

    // defines a mirus executable
    class mx
    {
    public:
        mx_header header;
    };
}

#endif
<|endoftext|>


<commit_before>/*
This demo shows how to use cvui in multiple windows relying on rows and colums.
Code licensed under the MIT license, check LICENSE file.
*/

#include <iostream>

#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>

#include "cvui.h"

#define WINDOW1_NAME "Windows 1"
#define WINDOW2_NAME "Windows 2"

int main(int argc, const char *argv[])
{
	// We have one mat for each window.
	cv::Mat frame1 = cv::Mat(600, 800, CV_8UC3), frame2 = cv::Mat(600, 800, CV_8UC3);

	// Create variables used by some components
	std::vector<double> window1_values;
	std::vector<double> window2_values;
	bool window1_checked = false, window1_checked2 = false;
	bool window2_checked = false, window2_checked2 = false;
	double window1_value = 1.0, window1_value2 = 1.0, window1_value3 = 1.0;
	double window2_value = 1.0, window2_value2 = 1.0, window2_value3 = 1.0;

	cv::Mat img = cv::imread("./lena-face.jpg", cv::IMREAD_COLOR);
	cv::Mat imgRed = cv::imread("./lena-face-red.jpg", cv::IMREAD_COLOR);
	cv::Mat imgGray = cv::imread("./lena-face-gray.jpg", cv::IMREAD_COLOR);

	int padding = 10;

	// Fill the vector with a few random values
	for (std::vector<double>::size_type i = 0; i < 20; i++) {
		window1_values.push_back(rand() + 0.);
		window2_values.push_back(rand() + 0.);
	}

	// Start two OpenCV windows
	cv::namedWindow(WINDOW1_NAME);
	cv::namedWindow(WINDOW2_NAME);

	// Init cvui and inform it to use the first window as the default one.
	cvui::init(WINDOW1_NAME);

	// Tell cvui to keep track of mouse events in window2 as well.
	cvui::watch(WINDOW2_NAME);

	while (true) {
		// Inform cvui that all subsequent component calls and events are related to window 1.
		cvui::context(WINDOW1_NAME);

		// Fill the frame with a nice color
		frame1 = cv::Scalar(49, 52, 49);

		cvui::beginRow(frame1, 10, 20, 100, 50);
			cvui::text("This is ");
			cvui::printf("a row");
			cvui::checkbox("checkbox", &window1_checked);
			cvui::window(80, 80, "window");
			cvui::rect(50, 50, 0x00ff00, 0xff0000);
			cvui::sparkline(window1_values, 50, 50);
			cvui::counter(&window1_value);
			cvui::button(100, 30, "Fixed");
			cvui::image(img);
			cvui::button(img, imgGray, imgRed);
		cvui::endRow();

		padding = 50;
		cvui::beginRow(frame1, 10, 150, 100, 50, padding);
			cvui::text("This is ");
			cvui::printf("another row");
			cvui::checkbox("checkbox", &window1_checked2);
			cvui::window(80, 80, "window");
			cvui::button(100, 30, "Fixed");
			cvui::printf("with 50px paddin7hg.");
		cvui::endRow();

		cvui::beginRow(frame1, 10, 250, 100, 50);
			cvui::text("This is ");
			cvui::printf("another row with a trackbar ");
			cvui::trackbar(150, &window1_value2, 0., 5.);
			cvui::printf(" and a button ");
			cvui::button(100, 30, "button");
		cvui::endRow();

		cvui::beginColumn(frame1, 50, 330, 100, 200);
			cvui::text("Column 1 (no padding)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::text("End of column 1");
		cvui::endColumn();

		padding = 10;
		cvui::beginColumn(frame1, 300, 330, 100, 200, padding);
			cvui::text("Column 2 (padding = 10)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::trackbar(150, &window1_value3, 0., 5., 1, "%3.2Lf", cvui::TRACKBAR_DISCRETE, 0.25);
			cvui::text("End of column 2");
		cvui::endColumn();

		cvui::beginColumn(frame1, 550, 330, 100, 200);
			cvui::text("Column 3 (use space)");
			cvui::space(5);
			cvui::button("button1 5px below");
			cvui::space(50);
			cvui::text("Text 50px below");
			cvui::space(20);
			cvui::button("Button 20px below");
			cvui::space(40);
			cvui::text("End of column 2 (40px below)");
		cvui::endColumn();

		// Update all components of window1, e.g. mouse clicks, and show it.
		cvui::update(WINDOW1_NAME);
		cv::imshow(WINDOW1_NAME, frame1);

		// From this point on, we are going to render the second window. We need to inform cvui
		// that all updates and components from now on are connected to window 2.
		// We do that by calling cvui::context().
		cvui::context(WINDOW2_NAME);
		frame2 = cv::Scalar(49, 52, 49);

		cvui::beginRow(frame2, 10, 20, 100, 50);
			cvui::text("This is ");
			cvui::printf("a row");
			cvui::checkbox("checkbox", &window2_checked);
			cvui::window(80, 80, "window");
			cvui::rect(50, 50, 0x00ff00, 0xff0000);
			cvui::sparkline(window2_values, 50, 50);
			cvui::counter(&window2_value);
			cvui::button(100, 30, "Fixed");
			cvui::image(img);
			cvui::button(img, imgGray, imgRed);
		cvui::endRow();

		padding = 50;
		cvui::beginRow(frame2, 10, 150, 100, 50, padding);
			cvui::text("This is ");
			cvui::printf("another row");
			cvui::checkbox("checkbox", &window2_checked2);
			cvui::window(80, 80, "window");
			cvui::button(100, 30, "Fixed");
			cvui::printf("with 50px paddin7hg.");
		cvui::endRow();

		// Another row mixing several components
		cvui::beginRow(frame2, 10, 250, 100, 50);
		cvui::text("This is ");
		cvui::printf("another row with a trackbar ");
		cvui::trackbar(150, &window2_value2, 0., 5.);
		cvui::printf(" and a button ");
		cvui::button(100, 30, "button");
		cvui::endRow();

		cvui::beginColumn(frame2, 50, 330, 100, 200);
			cvui::text("Column 1 (no padding)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::text("End of column 1");
		cvui::endColumn();

		padding = 10;
		cvui::beginColumn(frame2, 300, 330, 100, 200, padding);
			cvui::text("Column 2 (padding = 10)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::trackbar(150, &window2_value3, 0., 5., 1, "%3.2Lf", cvui::TRACKBAR_DISCRETE, 0.25);
			cvui::text("End of column 2");
		cvui::endColumn();

		cvui::beginColumn(frame2, 550, 330, 100, 200);
			cvui::text("Column 3 (use space)");
			cvui::space(5);
			cvui::button("button1 5px below");
			cvui::space(50);
			cvui::text("Text 50px below");
			cvui::space(20);
			cvui::button("Button 20px below");
			cvui::space(40);
			cvui::text("End of column 2 (40px below)");
		cvui::endColumn();

		// Update all components of window2, e.g. mouse clicks, and show it.
		cvui::update(WINDOW2_NAME);
		cv::imshow(WINDOW2_NAME, frame2);

		// Check if ESC key was pressed
		if (cv::waitKey(20) == 27) {
			break;
		}
	}

	return 0;
}<commit_msg>Add small comment<commit_after>/*
This demo shows how to use cvui in multiple windows relying on rows and colums.
Code licensed under the MIT license, check LICENSE file.
*/

#include <iostream>

#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>

#include "cvui.h"

#define WINDOW1_NAME "Windows 1"
#define WINDOW2_NAME "Windows 2"

int main(int argc, const char *argv[])
{
	// We have one mat for each window.
	cv::Mat frame1 = cv::Mat(600, 800, CV_8UC3), frame2 = cv::Mat(600, 800, CV_8UC3);

	// Create variables used by some components
	std::vector<double> window1_values;
	std::vector<double> window2_values;
	bool window1_checked = false, window1_checked2 = false;
	bool window2_checked = false, window2_checked2 = false;
	double window1_value = 1.0, window1_value2 = 1.0, window1_value3 = 1.0;
	double window2_value = 1.0, window2_value2 = 1.0, window2_value3 = 1.0;

	cv::Mat img = cv::imread("./lena-face.jpg", cv::IMREAD_COLOR);
	cv::Mat imgRed = cv::imread("./lena-face-red.jpg", cv::IMREAD_COLOR);
	cv::Mat imgGray = cv::imread("./lena-face-gray.jpg", cv::IMREAD_COLOR);

	int padding = 10;

	// Fill the vector with a few random values
	for (std::vector<double>::size_type i = 0; i < 20; i++) {
		window1_values.push_back(rand() + 0.);
		window2_values.push_back(rand() + 0.);
	}

	// Start two OpenCV windows
	cv::namedWindow(WINDOW1_NAME);
	cv::namedWindow(WINDOW2_NAME);

	// Init cvui and inform it to use the first window as the default one.
	// cvui::init() will automatically watch the informed window.
	cvui::init(WINDOW1_NAME);

	// Tell cvui to keep track of mouse events in window2 as well.
	cvui::watch(WINDOW2_NAME);

	while (true) {
		// Inform cvui that all subsequent component calls and events are related to window 1.
		cvui::context(WINDOW1_NAME);

		// Fill the frame with a nice color
		frame1 = cv::Scalar(49, 52, 49);

		cvui::beginRow(frame1, 10, 20, 100, 50);
			cvui::text("This is ");
			cvui::printf("a row");
			cvui::checkbox("checkbox", &window1_checked);
			cvui::window(80, 80, "window");
			cvui::rect(50, 50, 0x00ff00, 0xff0000);
			cvui::sparkline(window1_values, 50, 50);
			cvui::counter(&window1_value);
			cvui::button(100, 30, "Fixed");
			cvui::image(img);
			cvui::button(img, imgGray, imgRed);
		cvui::endRow();

		padding = 50;
		cvui::beginRow(frame1, 10, 150, 100, 50, padding);
			cvui::text("This is ");
			cvui::printf("another row");
			cvui::checkbox("checkbox", &window1_checked2);
			cvui::window(80, 80, "window");
			cvui::button(100, 30, "Fixed");
			cvui::printf("with 50px paddin7hg.");
		cvui::endRow();

		cvui::beginRow(frame1, 10, 250, 100, 50);
			cvui::text("This is ");
			cvui::printf("another row with a trackbar ");
			cvui::trackbar(150, &window1_value2, 0., 5.);
			cvui::printf(" and a button ");
			cvui::button(100, 30, "button");
		cvui::endRow();

		cvui::beginColumn(frame1, 50, 330, 100, 200);
			cvui::text("Column 1 (no padding)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::text("End of column 1");
		cvui::endColumn();

		padding = 10;
		cvui::beginColumn(frame1, 300, 330, 100, 200, padding);
			cvui::text("Column 2 (padding = 10)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::trackbar(150, &window1_value3, 0., 5., 1, "%3.2Lf", cvui::TRACKBAR_DISCRETE, 0.25);
			cvui::text("End of column 2");
		cvui::endColumn();

		cvui::beginColumn(frame1, 550, 330, 100, 200);
			cvui::text("Column 3 (use space)");
			cvui::space(5);
			cvui::button("button1 5px below");
			cvui::space(50);
			cvui::text("Text 50px below");
			cvui::space(20);
			cvui::button("Button 20px below");
			cvui::space(40);
			cvui::text("End of column 2 (40px below)");
		cvui::endColumn();

		// Update all components of window1, e.g. mouse clicks, and show it.
		cvui::update(WINDOW1_NAME);
		cv::imshow(WINDOW1_NAME, frame1);

		// From this point on, we are going to render the second window. We need to inform cvui
		// that all updates and components from now on are connected to window 2.
		// We do that by calling cvui::context().
		cvui::context(WINDOW2_NAME);
		frame2 = cv::Scalar(49, 52, 49);

		cvui::beginRow(frame2, 10, 20, 100, 50);
			cvui::text("This is ");
			cvui::printf("a row");
			cvui::checkbox("checkbox", &window2_checked);
			cvui::window(80, 80, "window");
			cvui::rect(50, 50, 0x00ff00, 0xff0000);
			cvui::sparkline(window2_values, 50, 50);
			cvui::counter(&window2_value);
			cvui::button(100, 30, "Fixed");
			cvui::image(img);
			cvui::button(img, imgGray, imgRed);
		cvui::endRow();

		padding = 50;
		cvui::beginRow(frame2, 10, 150, 100, 50, padding);
			cvui::text("This is ");
			cvui::printf("another row");
			cvui::checkbox("checkbox", &window2_checked2);
			cvui::window(80, 80, "window");
			cvui::button(100, 30, "Fixed");
			cvui::printf("with 50px paddin7hg.");
		cvui::endRow();

		// Another row mixing several components
		cvui::beginRow(frame2, 10, 250, 100, 50);
		cvui::text("This is ");
		cvui::printf("another row with a trackbar ");
		cvui::trackbar(150, &window2_value2, 0., 5.);
		cvui::printf(" and a button ");
		cvui::button(100, 30, "button");
		cvui::endRow();

		cvui::beginColumn(frame2, 50, 330, 100, 200);
			cvui::text("Column 1 (no padding)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::text("End of column 1");
		cvui::endColumn();

		padding = 10;
		cvui::beginColumn(frame2, 300, 330, 100, 200, padding);
			cvui::text("Column 2 (padding = 10)");
			cvui::button("button1");
			cvui::button("button2");
			cvui::trackbar(150, &window2_value3, 0., 5., 1, "%3.2Lf", cvui::TRACKBAR_DISCRETE, 0.25);
			cvui::text("End of column 2");
		cvui::endColumn();

		cvui::beginColumn(frame2, 550, 330, 100, 200);
			cvui::text("Column 3 (use space)");
			cvui::space(5);
			cvui::button("button1 5px below");
			cvui::space(50);
			cvui::text("Text 50px below");
			cvui::space(20);
			cvui::button("Button 20px below");
			cvui::space(40);
			cvui::text("End of column 2 (40px below)");
		cvui::endColumn();

		// Update all components of window2, e.g. mouse clicks, and show it.
		cvui::update(WINDOW2_NAME);
		cv::imshow(WINDOW2_NAME, frame2);

		// Check if ESC key was pressed
		if (cv::waitKey(20) == 27) {
			break;
		}
	}

	return 0;
}<|endoftext|>