Решатель линейных функций из двух точек (x, y)

10

Задание

Напишите функцию L (), которая принимает два аргумента Tuple координат в форме (x, y) и возвращает их соответствующую линейную функцию в форме (a, c), где a - коэффициент члена x, а c это у-перехват.

Можно предположить, что входные данные не будут линиями, перпендикулярными оси x, и что эти два входа являются отдельными точками.

счет 

Это Code Golf: самая короткая программа выигрывает.

Обратите внимание: не используйте никакие математические функции, кроме основных операторов (+, -, /, *).

пример

Вот мое решение для игры в гольф на Python.

def L(Point1, Point2):
    x = 0
    y = 1
    Gradient = (float(Point1[y]) - float(Point2[y])) / (float(Point1[x]) - float(Point2[x]))
    YIntercept = Point1[y] - Gradient * Point1[x] 
    return (Gradient, YIntercept)

Вывод:

>>> L( (0,0) , (1,1) )
(1.0, 0.0)

>>> L( (0,0) , (2,1) )
(0.5, 0.0)

>>> L( (0,0) , (7,1) )
(0.14285714285714285, 0.0)

>>> L( (10,22.5) , (5,12.5) )
(2.0, 2.5)
Гарри Бидл
источник
4
L( (0,0) , (0,1) )?
Говард
1
Вы можете предположить, что ввод не является линией, параллельной оси X.
Гарри Бидл
2
Вы можете предположить, что ввод не является линией, параллельной оси X. Вы имеете в виду ось Y?
Говард
Извините, редактирование поста было правильным, перпендикулярно оси X.
Гарри Бидл,
2
L((0,0),(0,0))?
user12205

Ответы:

1

J - 23 символа

Довольно просто. Определяет двоичный глагол Lдля использования в качестве (x1,y1) L (x2,y2).

L=:%~/@:-,-/@(*|.)%-&{.

Объяснение:

L=:%~/@:-,-/@(*|.)%-&{.  NB. the function L
                    &{.  NB. x coord of both points
                   -     NB. left x minus right x
             ( |.)       NB. flip right argument: (y2,x2)
              *          NB. pointwise multiplication of (x1,y1) and (y2,x2)
          -/@            NB. subtract the two results: (x1*y2)-(y1*x2)
                  %      NB. divide: (x1*y2 - y1*x2)/(x1-x2)
        -                NB. pointwise subtraction
   %~/@:                 NB. divide y difference by x diff: (y1-y2)/(x1-x2)
         ,               NB. append results together
L=:                      NB. assign function to L

Примеры:

   L=:%~/@:-,-/@(*|.)%-&{.
   0 0 L 1 1
1 0
   0 0 L 2 1
0.5 0
   0 0 L 7 1
0.142857 0
   10 22.5 L 5 12.5
2 2.5
   0 0 L 0 1  NB. __ is negative infinity
__ 0
algorithmshark
источник
7

GNU dc , 30 24 байта

[sysxly-rlx-/dlx*lyr-]sL

Определяет макрос так L, что (x 1 , y 1 , x 2 , y 2 ) должны быть помещены в стек в этом порядке перед вызовом, а после вызова L(a, c) могут быть извлечены из стека (в обратном порядке Конечно - это стек).

Testcase (сохранить как «linear.dc» и запустить dc linear.dc):

[sysxly-rlx- / dlx * lyr-] sL # Определить макрос L

10 # Нажмите x1 в стек
22.5 # Нажмите y1 в стек
5 # Нажмите x2 в стек
12.5 # Вставьте y2 в стек

LLx # Call L macro
f # Дамп стека

Выход:

$ dc linear.dc 
2.5
2
$ 

Объяснение макроса L:

  • syпоп 2, чтобы yзарегистрироваться
  • sxпоп х 2, чтобы xзарегистрироваться
  • lypush yрегистр (у 2 )
  • -вычесть y 2 из y 1
  • rпоменяйте местами (y 1 - y 2 ) и x 1 в стеке
  • lxнажимной xрегистр (х 2 )
  • -вычесть х 2 из х 1
  • /разделить (y 1 - y 2 ) на (x 1 - x 2 ), чтобы получить градиент
  • d двойной градиент
  • lxнажимной xрегистр (х 2 )
  • *умножить (х 2 ) на градиент
  • lypush yрегистр (у 2 )
  • rпоменять местами (y 2 ) и (x 2 * градиент) в стеке
  • -вычесть (x 2 * градиент) из (y 2 )
Цифровая травма
источник
1
Спасибо не плохо Я признаю, что меня избили. ;)
Мартин Эндер
1
@ m.buettner Re-golf и заново объяснил.
Цифровая травма
5

Хаскель, 41 персонаж

f(x,y)(u,v)=(a,y-a*x)where a=(y-v)/(x-u)

Не много для гольфа здесь. Это в значительной степени то, что вы обычно пишете без пробелов.

Хаммар
источник
4

Mathematica, 55 38 байт

Это было на удивление долго (эти надоедливые длинные имена функций ...) РЕДАКТИРОВАТЬ: Изменил подход для пересечения оси (черпая вдохновение из собственного ответа ОП). Оказывается, вычисление этого было не самой умной идеей.

L={g=1/Divide@@(#2-#),#[[2]]-g#[[1]]}&

Используйте как

L[{10,22.5},{5,12.5}]
> {2., 2.5}

Благодаря Mathematica вы также можете получить общий результат:

L[{r,s},{p,q}]
> {(p - r)/(q - s), (q r - p s)/(q - s)}

(Этот последний пример показывает, как я изначально это реализовал.)

Только для записи

L[{0,0},{0,1}]
> {ComplexInfinity, Indeterminate}

что технически правильно.

Мартин Эндер
источник
Аааа, офигенно, у меня была какая-то чёрная сумасшедшая мысль, что я буду винить в этом свою усталость
Гарри Бидл
1
+1. Почему ComplexInfinityи не старый добрый Infinity? (Я не знаю, Mathematica)
Цифровая травма
3
@DigitalTrauma Я думаю, это потому, что без явного указания Mathematica, что он может работать в действительных значениях, он всегда предполагает, что рассматриваемое пространство является комплексными числами, чтобы не выбрасывать сложные решения реальных уравнений.
Мартин Эндер
2

JavaScript, 62 48

Спасибо @Michael за игру в гольф с ES 6.

L=(a,b)=>[s=(b[1]-a[1])/(b[0]-a[0]),a[1]-s*a[0]]

Старая версия:

function L(a,b){return[s=(b[1]-a[1])/(b[0]-a[0]),a[1]-s*a[0]]}

Пример ввода:

L([0,0],[7,1])

Пример вывода:

[0.14285714285714285, 0]

Для записи:

L([0,0],[0,1])
[Infinity, NaN]
user12205
источник
46 с использованием ES6:L=(a,b)=>[g=(p=a[1]-b[1])/(q=a[0]-b[0]),p-g*q]
Майкл М.
@ Майкл Круто. Я новичок в JS, поэтому я не знал, что ты сможешь это сделать. Спасибо.
user12205
@ m.buettner Вы правы ... Исправлено
user12205
1
Теперь все ответы разделены ровно на десять символов. : D
Мартин Эндер
1
Awww. Кролик изменился!
Джастин
2

Python3 (51)

def L(p,q):x,y=p;X,Y=q;m=(Y-y)/(X-x);return m,y-x*m
XNOR
источник
2

C # 105 байт

Это не просто функция, и она будет полностью скомпилирована сама по себе. Я поставил Lв Systemпространстве имен Замыкание с помощью, но это лучше , чтобы полностью определить и сэкономить на использовании пространства имен. Сохранены скобки. Также экономия от return new z[]вreturn new[]

using z=System.Single;class P{z[] L(z[]a,z[]b){z c=(a[1]-b[1])/(a[0]-b[0]);return new[]{c,a[1]-c*a[0]};}}
Натан Купер
источник
Является ли (c*a[0])необходимым? Разве вы не можете удалить эти скобки и сохранить 2 байта?
Кайл Канос
@KyleKanos Да, спасибо. Хотя c # не использует BODMAS, умножение будет выполнено первым (я думаю).
Натан Купер
Я бы сказал, что вы должны включить namespaceдекларацию или изменить ее System.Single, чтобы это решение было действительным.
Тим С.
1

Lua 5.1.4: 66 64 байта

function L(q,w)a=(q[2]-w[2])/(q[1]-w[1])return a,q[2]-a*q[1];end

Пример использования:

> print(L( {0,0}, {1,0} ))
-0   0
> print(L( {0,0}, {1,1} ))
1    0
> print(L( {0,0}, {7,1} ))
0.14285714285714    0
> print(L( {0,0}, {0,1} ))
-inf   -nan
> print(L( {0,0}, {0,0} ))
-nan   -nan
Кайл Канос
источник
1

C ++ 88 (было 106)

Улучшено: спасибо за ваши комментарии.

struct t{double x,y;};
t L(t u, t v){u.x=(v.y-u.y)/(v.x-u.x);u.y=v.y-u.x*v.x;return u;}

Golfed:

typedef struct T{double x,y;}t;
t line(t u, t v){t z;z.x=(v.y-u.y)/(v.x-u.x);z.y=v.y-(z.x*v.x);return z;}

Источник

typedef struct T{
    double x,y;
} t;

t line(t u, t v)
{
t z;
z.x=(v.y-u.y)/(v.x-u.x);
z.y=v.y-(z.x*v.x);
return z;
}
bacchusbeale
источник
Я вижу ненужное пространство;)
Мартин Эндер
1
Если это C ++, почему typedef?
'42
Кроме того, я думаю, что вы можете избавиться от z:u.x=(v.y-u.y)/(v.x-u.x); u.y=v.y-z.x*v.x; return u;
Dyp
1

Apple Swift 95 86

Это может быть первая запись Swift на PCG.SE ??

func L(x:Float...)->(Float,Float){var a=(x[3]-x[1])/(x[2]-x[0]);return(a,x[1]-a*x[0])}

Я не вижу, чтобы этот язык был огромным хитом для сообщества Code Golf.

Гарри Бидл
источник
0

Golfscript: 25 байтов

~:y\:x;-\x--1?*.x-1**y+\p

Поскольку функция должна называться «L», я сохранил ее как «L.gs» локально.

Подвох, как объясняет @Dennis в этом посте , заключается в том, что нам нужно обманом заставить Golfscript использовать рациональные числа вместо целых. Так что это работает, если вы готовы принять ввод X1 Y1 X2 Y2 в нотации golfscript

# L( (0,0) , (1,1) )
echo "0 0 1 1" | golfscript L.gs
> 1/1
> 0/1
#L( (10,22.5) , (5,12.5) )
echo "10 22 2-1?+ 5 12 2-1?+" | golfscript L.gs
> 2/1
> 5/2
wrongu
источник
0

Рубин - 48 символов

Почти идентичный ответу JavaScript:

L=->u,v{a,b,c,d=*u,*v;[s=(d-b).fdiv(c-a),b-s*a]}
О.И.
источник
0

Python3 - 64 57 байт

def L(q,w):a=(q[1]-w[1])/(q[0]-w[0]);return a,q[1]-a*q[0]

Вы можете уменьшить его до 43, если не используете Tuple, что делают многие люди ...

def L(x,y,q,w):a=(x-q)/(y-w);return a,y-a*x
Гарри Бидл
источник
return(a,q[1]-a*q[0])
user12205
@ace Спасибо, это было небрежно
Гарри Бидл
0

PHP (75 символов)

function L($u,$v){return[$s=($v[1]-$u[1])/($v[0]-$u[0]),$v[1]-($s*$v[0])];}

тестовое задание : print_r(L([0,0],[7,1]));

вывод :

Array
(
    [0] => 0.14285714285714
    [1] => 0
)

(спасибо @ace)

Фабьен Са
источник