<commit_before>#!/usr/bin/python

def type_fun(r, runner, nargs, name, met):

    args = []

    if r:
        r = 'R'
    else:
        r = 'void'
    if runner:
        args += ['runner::Runner&']
    if not met:
        args += ['S']
    for i in range(nargs):
        args += ['Arg%s' % i]
    if met:
        met = 'S::'
    else:
        met = ''
    return '%s (%s*%s)(%s)' % (r, met, name, ', '.join(args))


def type_boost(r, runner, nargs, met):

    args = []

    if r:
        args += ['R']
    else:
        args += ['void']
    if runner:
        args += ['runner::Runner&']
    if met:
        # Keep trailing space to avoid '>>'
        args += ['libport::shared_ptr<S> ']
    else:
        args += ['S']
    for i in range(nargs):
        args += ['Arg%s' % i]

    return 'boost::function%s<%s>' % (len(args) - 1, ', '.join(args))


def any_to_boost_function(r, runner, nargs, met):

    params = []
    if r:
        params += ['typename R']
    params += ['typename S']
    for i in range(nargs):
        params += ['typename Arg%s' % i]

    if met and runner:
        args = ''
        for i in range(nargs):
            args += ', _%s' % (i + 3)
        body = 'return boost::bind((%s)(v), _2, _1%s);'\
          % (type_fun(r, runner, nargs, '', met), args)
    else:
        body = 'return type(v);';


    return '''\
    template <%(params)s>
    struct AnyToBoostFunction<%(fun)s>
    {
      typedef %(boost)s type;
      static type
      convert(%(named_fun)s)
      {
        %(body)s
      }
    };
''' % {
        'body': body,
        'boost': type_boost(r, runner, nargs, met),
        'fun': type_fun(r, runner, nargs, '', met),
        'named_fun': type_fun(r, runner, nargs, 'v', met),
        'params': ', '.join(params),
        }

print '''\
#ifndef ANY_TO_BOOST_FUNCTION_HXX
# define ANY_TO_BOOST_FUNCTION_HXX

# include <boost/function.hpp>
# include <object/cxx-helper.hh>
# include <runner/runner.hh>

namespace object
{
  template <typename T>
  T AnyToBoostFunction<T>::convert(T v)
  {
    // If you fail here, the given type is not supported for
    // conversion to boost::function
    return v;
  }

'''

for r in [True, False]:
    for runner in [True, False]:
        for met in [True, False]:
            for n in range(5):
                print '    // Return: %s, Runner: %s, Method: %s, Arguments: %s'\
                      % (r, runner, met, n)
                print any_to_boost_function(r, runner, n, met)

print '''\

  // Treat the case of argument-less functions manually
  namespace
  {
    template <typename R>
    R ignore_self(R (*f)(), rObject)
    {
      return f();
    }<commit_msg>Fix AnyToBoostFunction under windows.<commit_after>#!/usr/bin/python

def type_fun(r, runner, nargs, name, met):

    args = []

    if r:
        r = 'R'
    else:
        r = 'void'
    if runner:
        args += ['runner::Runner&']
    if not met:
        args += ['S']
    for i in range(nargs):
        args += ['Arg%s' % i]
    if met:
        met = 'S::'
    else:
        met = ''
    return '%s (%s*%s)(%s)' % (r, met, name, ', '.join(args))


def type_boost(r, runner, nargs, met):

    args = []

    if r:
        args += ['R']
    else:
        args += ['void']
    if runner:
        args += ['runner::Runner&']
    if met:
        # Keep trailing space to avoid '>>'
        args += ['libport::shared_ptr<S> ']
    else:
        args += ['S']
    for i in range(nargs):
        args += ['Arg%s' % i]

    return 'boost::function%s<%s>' % (len(args) - 1, ', '.join(args))


def any_to_boost_function(r, runner, nargs, met):

    params = []
    if r:
        params += ['typename R']
    params += ['typename S']
    for i in range(nargs):
        params += ['typename Arg%s' % i]

    if met and runner:
        args = ''
        for i in range(nargs):
            args += ', _%s' % (i + 3)
        body = 'return boost::bind((%s)(v), _2, _1%s);'\
          % (type_fun(r, runner, nargs, '', met), args)
    else:
        body = 'return type(v);';


    return '''\
    template <%(params)s>
    struct AnyToBoostFunction<%(fun)s>
    {
      typedef %(boost)s type;
      static type
      convert(%(named_fun)s)
      {
        %(body)s
      }
    };
''' % {
        'body': body,
        'boost': type_boost(r, runner, nargs, met),
        'fun': type_fun(r, runner, nargs, '', met),
        'named_fun': type_fun(r, runner, nargs, 'v', met),
        'params': ', '.join(params),
        }

print '''\
#ifndef ANY_TO_BOOST_FUNCTION_HXX
# define ANY_TO_BOOST_FUNCTION_HXX

# include <boost/function.hpp>
# include <object/cxx-helper.hh>
# include <runner/runner.hh>

namespace object
{
  template <typename T>
  T AnyToBoostFunction<T>::convert(T v)
  {
    // If you fail here, the given type is not supported for
    // conversion to boost::function
    return v;
  }

'''

# For now, only the r case is needed, and !r fails with visual studio
for r in [True]:
    for runner in [True, False]:
        for met in [True, False]:
            for n in range(5):
                print '    // Return: %s, Runner: %s, Method: %s, Arguments: %s'\
                      % (r, runner, met, n)
                print any_to_boost_function(r, runner, n, met)

print '''\

  // Treat the case of argument-less functions manually
  namespace
  {
    template <typename R>
    R ignore_self(R (*f)(), rObject)
    {
      return f();
    }
{'fraction_non_alphanumeric': 0.16916527854895427, 'fraction_numerical': 0.0018508236165093468, 'mean_word_length': 2.0139431121026212, 'pattern_counts': {'":': 0, '<': 23, '<?xml version=': 0, '>': 27, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4215186', 'n_tokens_mistral': 1909, 'n_tokens_neox': 1859, 'n_words': 528}