Cuộc thi biểu hiện toán học!


15

Bạn được cung cấp 6 số: 5 chữ số [0-9] và một số mục tiêu. Mục tiêu của bạn là xen kẽ các toán tử giữa các chữ số để đến gần nhất có thể với mục tiêu. Bạn phải sử dụng chính xác từng chữ số một lần và có thể sử dụng các toán tử sau bao nhiêu lần tùy ý : + - * / () ^ sqrt sin cos tan. Ví dụ, nếu tôi được cung cấp, 8 2 4 7 2 65tôi có thể xuất ra 82-(2*7)-4. Điều này đánh giá là 64, do đó cho tôi điểm 1 vì tôi cách mục tiêu 1 điểm. Lưu ý: Bạn không thể đặt dấu thập phân giữa các chữ số.

Tôi đang sử dụng mã từ này câu trả lời StackOverflow để đánh giá các biểu thức toán học. Ở dưới cùng của câu hỏi này có các chương trình bạn có thể sử dụng để kiểm tra nó.

Chức năng xâu chuỗi (Cập nhật!)

@mdahmoune đã tiết lộ một mức độ phức tạp mới cho thử thách này. Như vậy, tôi đang thêm một tính năng mới: xâu chuỗi các chức năng đơn nguyên. Điều này hoạt động trên sin, cos, tan và sqrt. Bây giờ thay vì viết sin(sin(sin(sin(10)))), bạn có thể viết sin_4(10). Hãy thử nó trong đánh giá!

Đầu vào

200 trường hợp kiểm tra phân tách dòng gồm 5 chữ số và một số mục tiêu được phân tách bằng dấu cách. Bạn có thể sử dụng chương trình ở cuối câu hỏi để tạo các trường hợp kiểm tra mẫu, nhưng tôi sẽ có các trường hợp kiểm tra riêng để chấm điểm chính thức. Các trường hợp thử nghiệm được chia thành 5 phần của 40 thử nghiệm với các phạm vi sau cho số mục tiêu:

  • Mục 1: [0,1] (đến 5 điểm thập phân)
  • Mục 2: [0,10] (đến 4 điểm thập phân)
  • Mục 3: [0,1000] (đến 3 điểm thập phân)
  • Mục 4: [0,10 6 ] (đến 1 dấu thập phân)
  • Mục 5: [0,10 9 ] (đến 0 điểm thập phân)

Đầu ra

200 biểu thức toán học tách dòng. Ví dụ: nếu trường hợp kiểm tra là 5 6 7 8 9 25.807, một đầu ra có thể có thể là78-59+6

Chấm điểm

Mục tiêu mỗi vòng là để đến gần số mục tiêu hơn các chương trình cạnh tranh khác. Tôi sẽ sử dụng tính năng ghi điểm Mario Kart 8 , đó là : . Nếu nhiều câu trả lời có cùng số điểm chính xác, các điểm được chia đều, làm tròn đến int gần nhất. Ví dụ: nếu các chương trình ở vị trí thứ 5-8 được gắn kết, chúng sẽ nhận được (8 + 7 + 6 + 5) / 4 = 6,5 => 7 điểm trong vòng đó. Kết thúc 200 vòng, chương trình nào có nhiều điểm nhất sẽ chiến thắng. Nếu hai chương trình có cùng số điểm ở cuối, thì bộ ngắt kết nối là chương trình hoàn thành chạy nhanh hơn.1st: 15 2nd: 12 3rd: 10 4th: 9 5th: 8 6th: 7 7th: 6 8th: 5 9th: 4 10th: 3 11th: 2 12th: 1 13th+: 0

Quy tắc

  1. Bạn chỉ có thể sử dụng một trong những ngôn ngữ thường được cài đặt sẵn trên Mac như C, C ++, Java, PhP, Perl, Python (2 hoặc 3), Ruby và Swift. Nếu bạn có một ngôn ngữ bạn muốn sử dụng với trình biên dịch / trình thông dịch là một bản tải xuống tương đối nhỏ, tôi có thể thêm nó vào. Bạn cũng có thể sử dụng ngôn ngữ với trình thông dịch trực tuyến, nhưng ngôn ngữ đó sẽ không chạy nhanh như vậy.
  2. Chỉ định trong câu trả lời của bạn nếu bạn muốn các hàm lượng giác được tính theo độ hoặc radian .
  3. Chương trình của bạn phải xuất các giải pháp cho tất cả 200 trường hợp thử nghiệm (sang tệp hoặc STDOUT) trong vòng 60 giây trên máy Mac của tôi.
  4. Sự ngẫu nhiên phải được gieo hạt.
  5. Tổng sản lượng của bạn cho tất cả các trường hợp thử nghiệm không thể nhiều hơn 1 MB .
  6. Nếu bạn đã cải thiện giải pháp của mình và muốn được chấm điểm lại, hãy thêm Điểm lại ở đầu câu trả lời của bạn in đậm.

Chương trình

(thay đổi đối số "deg" thành "rad" nếu bạn muốn radian)

  1. Kiểm tra đánh giá
  2. Điểm số đầu ra của chương trình cho các trường hợp thử nghiệm
  3. Tạo các trường hợp thử nghiệm:

document.getElementById("but").onclick = gen;
var checks = document.getElementById("checks");
for(var i = 1;i<=6;i++) {
var val = i<6 ? i : "All";
var l = document.createElement("label");
l.for = "check" + val;
l.innerText = " "+val+" ";
checks.appendChild(l);
  var check = document.createElement("input");
  check.type = "checkBox";
  check.id = "check"+val;
  if(val == "All") {
  check.onchange = function() {
  if(this.checked == true)  {
  for(var i = 0;i<5;i++) {
    this.parentNode.elements[i].checked = true;
  }
  }
};  
  }
  else {
  check.onchange = function() {
    document.getElementById("checkAll").checked = false;
  }
  }
  checks.appendChild(check);
  
}



function gen() {
var tests = [];
var boxes = checks.elements;
if(boxes[0].checked)genTests(tests,1,5,40);
if(boxes[1].checked)genTests(tests,10,4,40);
if(boxes[2].checked)genTests(tests,1000,3,40);
if(boxes[3].checked)genTests(tests,1e6,1,40);
if(boxes[4].checked)genTests(tests,1e9,0,40);
document.getElementById("box").value =  tests.join("\n");
}

function genTests(testArray,tMax,tDec,n) {
for(var i = 0;i<n;i++) {
  testArray.push(genNums(tMax,tDec).join(" "));
}
}

function genNums(tMax,tDec) {
var nums = genDigits();
nums.push(genTarget(tMax,tDec));
return nums;
}

function genTarget(tMax,tDec) {
  return genRand(tMax,tDec);
}

function genRand(limit,decimals) {
  var r = Math.random()*limit;
  return r.toFixed(decimals);
}

function genDigits() {
  var digits = [];
   for(var i = 0;i<5;i++) {
    digits.push(Math.floor(Math.random()*10));
   }
   return digits;
}
textarea {
  font-size: 14pt;
  font-family: "Courier New", "Lucida Console", monospace;
}

div {
text-align: center;
}
<div>
<label for="checks">Sections: </label><form id="checks"></form>
<input type="button" id="but" value="Generate Test Cases" /><br/><textarea id="box" cols=20 rows=15></textarea>
</div>

Bảng xếp hạng

  1. người dùng202729 ( C ++ ): 2856, 152 trận thắng
  2. mdahmoune ( Python 2 ) [v2]: 2544, 48 trận thắng

Điểm số phần (# chiến thắng):

  1. [0-1] người dùng202729 : 40, mdahmoune: 0
  2. [0-10] người dùng202729 : 40, mdahmoune: 0
  3. [0-1000] người dùng202729 : 39, mdahmoune: 1
  4. [0-10 6 ] người dùng202729 : 33, mdahmoune: 7
  5. [0-10 9 ] người dùng202729: 0, mdahmoune : 40

Liên quan: Tạo phương trình hợp lệ bằng các số do người dùng chỉ định


Có bất kỳ lý do cụ thể các hàm lượng giác phải sử dụng độ? Có thể thêm một tùy chọn cho câu trả lời để chỉ định radian hoặc độ?
notjagan

Tập hợp các chữ số có nhất thiết phải là một chữ số khác không?
mdahmoune

@mdahmoune Các trường hợp kiểm tra được tạo ngẫu nhiên, vì vậy các chữ số có thể là 0. Bạn chỉ cần cố gắng hết sức trong tình huống đó. Trong chế độ độ, tôi có thể đạt được tới 3283,14 với cos(0)/sin(0^0)/sin(0^0).
geokavel

Thanx cho câu trả lời hoàn chỉnh của bạn :)
mdahmoune

Đây có phải là phương pháp tính điểm giống nhau cho 5 phần khác nhau không? Vắng (target_value-created_expression_value)? Tôi
mdahmoune

Câu trả lời:


3

C ++

// This program use radian mode

//#define DEBUG

#ifdef DEBUG
#define _GLIBCXX_DEBUG
#include <cassert>
#else
#define assert(x) void(0)
#endif

namespace std {
    /// Used for un-debug.
    struct not_cerr_t {
    } not_cerr;
}

template <typename T>
std::not_cerr_t& operator<<(std::not_cerr_t& not_cerr, T) {return not_cerr;}

#include <iostream>
#include <iomanip>
#include <cmath>
#include <limits>
#include <array>
#include <bitset>
#include <string>
#include <sstream>

#ifndef DEBUG
#define cerr not_cerr
#endif // DEBUG


// String conversion functions, because of some issues with MinGW
template <typename T>
T from_string(std::string st) {
    std::stringstream sst (st);
    T result;
    sst >> result;
    return result;
}

template <typename T>
std::string to_string(T x) {
    std::stringstream sst;
    sst << x;
    return sst.str();
}

template <typename T> int sgn(T val) {
    return (T(0) < val) - (val < T(0));
}


const int N_ITER = 1000, N_DIGIT = 5, NSOL = 4;
std::array<int, N_DIGIT> digits;
double target;

typedef std::bitset<N_ITER> stfunc; // sin-tan expression
// where sin = 0, tan = 1

double eval(const stfunc& fn, int length, double value) {
    while (length --> 0) {
        value = fn[length] ? std::tan(value) : std::sin(value);
    }
    return value;
}

struct stexpr { // just a stfunc with some information
    double x = 0, val = 0; // fn<length>(x) == val
    int length = 0;
    stfunc fn {};
//    bool operator[] (const int x) {return fn[x];}
    double eval() {return val = ::eval(fn, length, x);}
};

struct expr { // general form of stexpr
    // note that expr must be *always* atomic.
    double val = 0;
    std::string expr {};

    void clear() {
        val = 0;
        expr.clear();
    }

    // cos(cos(x)) is in approx 0.5 - 1,
    // so we can expect that sin(x) and tan(x) behaves reasonably nice
    private: void wrapcos2() {
        expr = "(cos_2 " + expr + ")"; // we assume that all expr is atomic
        val = std::cos(std::cos(val));
    }

    public: void wrap1() {
        if (val == 0) {
            expr = "(cos " + expr + ")"; // we assume that all expr is atomic
            val = std::cos(val);
        }
        if (val == 1) return;
        wrapcos2(); // range 0.54 - 1
        int cnt_sqrt = 0;
        for (int i = 0; i < 100; ++i) {
            ++cnt_sqrt;
            val = std::sqrt(val);
            if (val == 1) break;
        }
        expr = "(sqrt_" + to_string(cnt_sqrt) + " " + expr + ")"; // expr must be atomic
    }
};

stexpr nearest(double initial, double target) {
    stexpr result; // built on the fn of that
    result.x = initial;
    double value [N_ITER + 1];
    value[0] = initial;
    for (result.length = 1; result.length <= N_ITER; ++result.length) {
        double x = value[result.length-1];
        if (x < target) {
            result.fn[result.length-1] = 1;
        } else if (x > target) {
            result.fn[result.length-1] = 0;
        } else { // unlikely
            --result.length;
//            result.val = x;
            result.eval();
            assert(result.val == x);
            return result;
        }
        value[result.length] = result.eval(); // this line takes most of the time
        if (value[result.length] == value[result.length-1])
            break;
    }

//    for (int i = 0; i < N_ITER; ++i) {
//        std::cerr << i << '\t' << value[i] << '\t' << (value[i] - target) << '\n';
//    }

    double mindiff = std::numeric_limits<double>::max();
    int resultlength = -1;
    result.length = std::min(N_ITER, result.length);
    for (int l = 0; l <= result.length; ++l) {
        if (std::abs(value[l] - target) < mindiff) {
            mindiff = std::abs(value[l] - target);
            resultlength = l;
        }
    }

    result.length = resultlength;
    double val = value[resultlength];
    assert(std::abs(val - target) == mindiff);
    if (val != target) { // second-order optimization
        for (int i = 1; i < result.length; ++i) {
            // consider pair (i-1, i)
            if (result.fn[i-1] == result.fn[i]) continue; // look for (sin tan) or (tan sin)
            if (val < target && result.fn[i-1] == 0) { // we need to increase val : sin tan -> tan sin
                result.fn[i-1] = 1;
                result.fn[i] = 0;
                double newvalue = result.eval();
//                if (!(newvalue >= val)) std::cerr << "Floating point sin-tan error 1\n";
                if (std::abs(newvalue - target) < std::abs(val - target)) {
//                    std::cerr << "diff improved from " << std::abs(val - target) << " to " << std::abs(newvalue - target) << '\n';
                    val = newvalue;
                } else {
                    result.fn[i-1] = 0;
                    result.fn[i] = 1; // restore
                    #ifdef DEBUG
                    result.eval();
                    assert(val == result.val);
                    #endif // DEBUG
                }
            } else if (val > target && result.fn[i-1] == 1) {
                result.fn[i-1] = 0;
                result.fn[i] = 1;
                double newvalue = result.eval();
//                if (!(newvalue <= val)) std::cerr << "Floating point sin-tan error 2\n";
                if (std::abs(newvalue - target) < std::abs(val - target)) {
//                    std::cerr << "diff improved from " << std::abs(val - target) << " to " << std::abs(newvalue - target) << '\n';
                    val = newvalue;
                } else {
                    result.fn[i-1] = 1;
                    result.fn[i] = 0; // restore
                    #ifdef DEBUG
                    result.eval();
                    assert(val == result.val);
                    #endif // DEBUG
                }
            }
        }
    }
    double newdiff = std::abs(val - target);
    if (newdiff < mindiff) {
        mindiff = std::abs(val - target);
        std::cerr << "ok\n";
    } else if (newdiff > mindiff) {
        std::cerr << "Program error : error value = " << (newdiff - mindiff) << " (should be <= 0 if correct) \n";
        std::cerr << "mindiff = " << mindiff << ", newdiff = " << newdiff << '\n';
    }
    result.eval(); // set result.result
    assert(val == result.val);

    return result;
}

expr nearest(const expr& in, double target) {
    stexpr tmp = nearest(in.val, target);
    expr result;
    for (int i = 0; i < tmp.length; ++i)
        result.expr.append(tmp.fn[i] ? "tan " : "sin ");

    result.expr = "(" + result.expr + in.expr + ")";
    result.val = tmp.val;
    return result;
}

int main() {
    double totalscore = 0;

    assert (std::numeric_limits<double>::is_iec559);
    std::cerr << std::setprecision(23);

//    double initial = 0.61575952241185627;
//    target = 0.6157595200093855;
//    stexpr a = nearest(initial, target);
//    std::cerr << a.val << ' ' << a.length << '\n';
//    return 0;

    while (std::cin >> digits[0]) {
        for (unsigned i = 1; i < digits.size(); ++i) std::cin >> digits[i];
        std::cin >> target;

/*        std::string e;
//        int sum = 0;
//        for (int i : digits) {
//            sum += i;
//            e.append(to_string(i)).push_back('+');
//        }
//        e.pop_back(); // remove the last '+'
//        e = "cos cos (" + e + ")";
//        double val = std::cos(std::cos((double)sum));
//
//        stexpr result = nearest(val, target); // cos(cos(x)) is in approx 0.5 - 1,
//        // so we can expect that sin(x) and tan(x) behaves reasonably nice
//        std::string fns;
//        for (int i = 0; i < result.length; ++i) fns.append(result.fn[i] ? "tan" : "sin").push_back(' ');
//
//        std::cout << (fns + e) << '\n';
//        continue;*/

        std::array<expr, NSOL> sols;
        expr a, b, c, d; // temporary for solutions

        /* ----------------------------------------
           solution 1 : nearest cos cos sum(digits) */

        a.clear();
        for (int i : digits) {
            a.val += i; // no floating-point error here
            a.expr.append(to_string(i)).push_back('+');
        }
        a.expr.pop_back(); // remove the last '+'
        a.expr = "(" + a.expr + ")";
        a.wrap1();

        sols[0] = nearest(a, target);


        /* -----------------------------------------
              solution 2 : a * tan(b) + c (also important) */

        // find b first, then a, then finally c
        a.clear(); b.clear(); c.clear(); // e = a, b = e1, c = e2

        a.expr = to_string(digits[0]);
        a.val = digits[0];
        a.wrap1();

        b.expr = "(" + to_string(digits[1]) + "+" + to_string(digits[2]) + ")";
        b.val = digits[1] + digits[2];
        b.wrap1();

        c.expr = to_string(digits[3]);
        c.val = digits[3];
        c.wrap1();

        d.expr = to_string(digits[4]);
        d.val = digits[4];
        d.wrap1();

        b = nearest(b, std::atan(target));

        double targetA = target / std::tan(b.val);
        int cnt = 0;
        while (targetA < 1 && targetA > 0.9) {
            ++cnt;
            targetA = targetA * targetA;
        }
        a = nearest(a, targetA);
        while (cnt --> 0) {
            a.val = std::sqrt(a.val);
            a.expr = "sqrt " + a.expr;
        }
        a.expr = "(" + a.expr + ")"; // handle number of the form 0.9999999999

        /// partition of any number to easy-to-calculate sum of 2 numbers
        {{{{{{{{{{{{{{{{{{{{{{{{{{{{}}}}}}}}}}}}}}}}}}}}}}}}}}}}

        double targetC, targetD; // near 1, not in [0.9, 1), >= 0.1
        // that is, [0.1, 0.9), [1, inf)

        double target1 = target - (a.val * std::tan(b.val));

        double ac = std::abs(target1), sc = sgn(target1);
        if (ac < .1) targetC = 1 + ac, targetD = -1;
        else if (ac < 1) targetC = 1 + ac/2, targetD = ac/2 - 1;
        else if (ac < 1.8 || ac > 2) targetC = targetD = ac/2;
        else targetC = .8, targetD = ac - .8;

        targetC *= sc; targetD *= sc;

        c = nearest(c, std::abs(targetC)); if (targetC < 0) c.val = -c.val, c.expr = "(-" + c.expr + ")";
        d = nearest(d, std::abs(targetD)); if (targetD < 0) d.val = -d.val, d.expr = "(-" + d.expr + ")";

        sols[1].expr = a.expr + "*tan " + b.expr + "+" + c.expr + "+" + d.expr;
        sols[1].val = a.val * std::tan(b.val) + c.val + d.val;

        std::cerr
        << "\n---Method 2---"
        << "\na = " << a.val
        << "\ntarget a = " << targetA
        << "\nb = " << b.val
        << "\ntan b = " << std::tan(b.val)
        << "\nc = " << c.val
        << "\ntarget c = " << targetC
        << "\nd = " << d.val
        << "\ntarget d = " << targetD
        << "\n";

        /* -----------------------------------------
              solution 3 : (b + c) */

        target1 = target / 2;
        b.clear(); c.clear();

        for (int i = 0; i < N_DIGIT; ++i) {
            expr &ex = (i < 2 ? b : c);
            ex.val += digits[i];
            ex.expr.append(to_string(digits[i])).push_back('+');
        }
        b.expr.pop_back();
        b.expr = "(" + b.expr + ")";
        b.wrap1();

        c.expr.pop_back();
        c.expr = "(" + c.expr + ")";
        c.wrap1();

        b = nearest(b, target1);
        c = nearest(c, target - target1); // approx. target / 2

        sols[2].expr = "(" + b.expr + "+" + c.expr + ")";
        sols[2].val = b.val + c.val;

        /* -----------------------------------------
              solution 4 : a (*|/) (b - c)  (important) */

        a.clear(); b.clear(); c.clear(); // a = a, b = e1, c = e2

        a.expr = to_string(digits[0]);
        a.val = digits[0];
        a.wrap1();

        b.expr = "(" + to_string(digits[1]) + "+" + to_string(digits[2]) + ")";
        b.val = digits[1] + digits[2];
        b.wrap1();

        c.expr = "(" + to_string(digits[3]) + "+" + to_string(digits[4]) + ")";
        c.val = digits[3] + digits[4];
        c.wrap1();


        // (b-c) should be minimized
        bool multiply = target < a.val;
        double factor = multiply ? target / a.val : a.val / target;

        target1 = 1 + 2 * factor; // 1 + 2 * factor and 1 + factor

        std::cerr << "* Method 4 :\n";
        std::cerr << "b initial = " << b.val << ", target = " << target1 << ", ";
        b = nearest(b, target1);
        std::cerr << " get " << b.val << '\n';

        std::cerr << "c initial = " << c.val << ", target = " << b.val - factor << ", ";
        c = nearest(c, b.val - factor); // factor ~= e1.val - e2.val
        std::cerr << " get " << c.val << '\n';

        sols[3].expr = "(" + a.expr + (multiply ? "*(" : "/(") +
        ( b.expr + "-" + c.expr )
        + "))";
        factor = b.val - c.val;
        sols[3].val = multiply ? a.val * factor : a.val / factor;

        std::cerr << "a.val = " << a.val << '\n';

        /* ----------------------------------
                    Final result */

        int minindex = 0;
        assert(NSOL != 0);
        for (int i = 0; i < NSOL; ++i) {
            if (std::abs(target - sols[i].val) < std::abs(target - sols[minindex].val)) minindex = i;
            std::cerr << "Sol " << i << ", diff = " << std::abs(target - sols[i].val) << "\n";
        }
        std::cerr << "Choose " << minindex << "; target = " << target << '\n';
        totalscore += std::abs(target - sols[minindex].val);

        std::cout << sols[minindex].expr << '\n';
    }

    // #undef cerr // in case no-debug
    std::cerr << "total score = " << totalscore << '\n';
}

Đầu vào từ đầu vào tiêu chuẩn, đầu ra đến đầu ra tiêu chuẩn.


Có, tôi nghĩ <1MB. Lưu ý rằng nếu chương trình vi phạm thứ gì đó bạn có thể giảm N_ITER(hiện tại là 1000)
user202729

@geokavel Bây giờ có vấn đề nếu 1 / sin_100000000 (2)được phép, hoặc sin_1.374059274 (1).
dùng202729

1 / sin_100000000 (2)được cho phép nếu bạn có các chữ số 1 và 2 theo ý của bạn. Tôi không biết làm thế nào sin_1.374059274sẽ làm việc. Nó có nghĩa gì khi lặp lại sin một số lần không nguyên?
geokavel

@geokavel Nhưng công thức trước đây cần mãi mãi để đánh giá, vì vậy không khó để tính điểm. Cái sau có thể được định nghĩa en.wikipedia.org/wiki/ đá | Làm thế nào là chương trình về các trường hợp thử nghiệm chính thức?
dùng202729

Tôi thấy ý của bạn khi lặp lại một phần, nhưng tôi nghĩ rằng quá khó để tôi thực hiện nó. Chương trình của bạn chạy trong thời gian tốt - chỉ khoảng 25 giây.
geokavel

2

Python 2 , radian, điểm 0,0032 trong bài kiểm tra chính thức

Đây là giải pháp dự thảo thứ hai cho điểm trung bình 0,0032 điểm. Vì nó sử dụng một thành phần của rất nhiều sintôi đã sử dụng ký hiệu nhỏ gọn sau đây cho công thức đầu ra:

  • sin_1 x=sin(x)
  • sin_2 x=sin(sin(x))
  • ...
  • sin_7 x=sin(sin(sin(sin(sin(sin(sin(x)))))))
  • ...
import math
import bisect
s1=[[float(t) for t in e.split()] for e in s0.split('\n')]
maxi=int(1e7)
A=[]
B=[]
C=[]
D=[]
a=1
for i in range(maxi):
	A.append(a)
	C.append(1/a)
	b=math.sin(a)
	c=a-b
	B.append(1/c)
	D.append(c)
	a=b
B.sort() 
C.sort() 
A.sort() 
D.sort() 
d15={0:'sqrt_100 tan_4 cos_2 sin 0',1:'sqrt_100 tan_4 cos_2 sin 1',2:'sqrt_100 tan_2 cos_2 sin 2',3:'sqrt_100 tan_4 cos_2 sin 3',4:'sqrt_100 tan_4 cos_2 sin 4',5:'sqrt_100 tan_4 cos_2 sin 5',6:'sqrt_100 tan_4 cos_2 sin 6',7:'sqrt_100 tan_2 cos_2 sin 7',8:'sqrt_100 tan_2 cos_2 sin 8',9:'sqrt_100 tan_4 cos_2 sin 9'}
def d16(d):return '('+d15[d]+')'

def S0(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(B, r)-1
	w1=abs(r-B[i1])
	i2=bisect.bisect(C, w1)-1
	w2=abs(w1-C[i2]) 
	s='('+d16(a1)+'/(sin_'+str(i1)+' '+d16(a2)+'-'+'sin_'+str(i1+1)+' '+d16(a3)+')'+'+'+d16(a4)+'/sin_'+str(i2)+' '+d16(a5)+')'
	return (w2,s)

def S1(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(C, r)-1
	w1=abs(r-C[i1])
	i2=bisect.bisect(A, w1)-1
	w2=abs(w1-A[i2]) 
	s='('+d16(a1)+'/sin_'+str(i1)+' '+d16(a2)+'+sin_'+str(maxi-i2-1)+' ('+d16(a3)+'*'+d16(a4)+'*'+d16(a5)+')'
	return (w2,s)

def S2(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(A, r)-1
	w1=abs(r-A[i1])
	i2=bisect.bisect(D, w1)-1
	w2=abs(w1-D[i2]) 
	s='('+'(sin_'+str(maxi-i2-1)+' '+d16(a1)+'-'+'sin_'+str(maxi-i2)+' '+d16(a2)+')'+'+sin_'+str(maxi-i1-1)+' ('+d16(a3)+'*'+d16(a4)+'*'+d16(a5)+'))'
	return (w2,s)

def S3(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(A, r)-1
	w2=abs(r-A[i1])
	s='('+'sin_'+str(maxi-i1-1)+' ('+d16(a1)+'*'+d16(a2)+'*'+d16(a3)+'*'+d16(a4)+'*'+d16(a5)+'))'
	return (w2,s)

def S4(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(B, r)-1
	w2=abs(r-B[i1])
	s='('+d16(a1)+'/(sin_'+str(i1)+' '+d16(a2)+'-'+'sin_'+str(i1+1)+' '+d16(a3)+'*'+d16(a4)+'*'+d16(a5)+')'+')'
	return (w2,s)

def S5(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(C, r)-1
	w2=abs(r-C[i1])
	s='('+d16(a1)+'/sin_'+str(i1)+' '+d16(a2)+'*'+d16(a3)+'*'+d16(a4)+'*'+d16(a5)+')'
	return (w2,s)

def S6(l):
	cpt=0
	d=l[:-1]
	r=l[-1]
	a1,a2,a3,a4,a5=[int(t) for t in d]
	i1=bisect.bisect(D, r)-1
	w2=abs(r-D[i1])
	s='(sin_'+str(maxi-i1-1)+' '+d16(a1)+'-'+'sin_'+str(maxi-i1)+' '+d16(a2)+'*'+d16(a3)+'*'+d16(a4)+'*'+d16(a5)+')'
	return (w2,s)

def all4(s1):
	s=0
	for l in s1:
		f=min(S0(l),S1(l),S2(l),S3(l),S4(l),S5(l),S6(l))
		print f[1]
		s+=f[0]
	s/=len(s1)
	print 'average unofficial score:',s
all4(s1)

Hãy thử trực tuyến!


1
Chương trình của bạn nhận được số điểm 49,70 trong các bài kiểm tra chính thức. Vì một số lý do, nó thực sự không tốt trong trường hợp thử nghiệm trong phần 3 với các chữ số sau : 6 7 8 0 1.
geokavel

Chương trình của bạn xuất ra +(tan_4 cos_2 sin 6)/(sin_0((-(tan_4 cos_2 sin 7)-(tan_4 cos_2 sin 8)+(tan_4 cos_2 sin 0)+(tan_4 cos_2 sin 1))))cho trường hợp thử nghiệm đó, bằng 0,145.
geokavel

Xin lỗi, tôi đã viết điểm kiểm tra chính thức của bạn sai lần đầu tiên. Bạn thực sự làm tồi tệ hơn một chút so với trung bình trong các bài kiểm tra chính thức.
geokavel
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.