현지 맥시마와 미니 마 찾기


14

정의

주어진 함수의 최대 값과 최소값은 주어진 범위 내에서 또는 함수의 전체 도메인 내에서 함수의 최대 값과 최소값입니다.

도전

문제는 원하는 다항식을 사용하여 주어진 다항식 함수의 극대 최대 값과 최소값찾는 입니다. 걱정하지 마십시오. 나는 도전을 설명하고 가능한 한 단순하게 유지하기 위해 최선을 다할 것입니다.

입력 값은 단일 가변 다항식의 모든 계수 를 거듭 제곱의 증가 또는 증가 순서로 포함합니다 (사용자까지). 예를 들어

  • [3,-7,1] 대표 할 것이다 3x2 - 7x + 1 = 0
  • [4,0,0,-3] 대표 할 것이다 4x3-3=0.

해결 방법 (미분 사용)?

이제 우리의 입력이 [1,-12,45,8]이고, 함수에 불과 하다고 가정 해 봅시다 .x3 - 12x2 + 45x + 8

  1. 첫 번째 작업은 해당 함수의 파생물을 찾는 것입니다. 다항식 함수이므로 실제로 수행해야 할 간단한 작업입니다.

    의 미분은 입니다 . 존재하는 상수 항 은 단순히 곱해집니다. 또한 더하기 / 빼기 된 용어가 있으면 해당 파생어도 각각 더하거나 빼기합니다. 상수 수치의 미분 값은 0입니다. 다음은 몇 가지 예입니다.xnn*xn-1xn

    • x3 -> 3x2
    • 9x4 -> 9*4*x3 = 36x3
    • -5x2 -> -5*2*x = - 10x
    • 2x3 - 3x2 + 7x -> 6x2 - 6x + 7
    • 4x2 - 3 -> 8x - 0 = 8x
  2. 이제 새로운 다항식을 0에 동일하게하여 방정식을 풀고 x의 정수 값만 얻으십시오.

  3. x 값을 원래 함수에 넣고 결과를 반환하십시오. 출력이되어야합니다 .

앞에서 언급 한 예를 보자 [1,-12,45,8].

  • 입력: [1,-12,45,8]
  • 함수: x3 - 12x2 + 45x + 8
  • 미분-> 3x2 - 24x + 45 + 0 -> [3,-24,45]
  • 방정식을 해결 , 우리는 얻을 또는 .3x2 - 24x + 45 = 0x = 3x = 5
  • 이제 퍼팅 x = 3x = 5기능에, 우리는 값을 얻을 (62,58).
  • 출력-> [62,58]

가정

  1. 모든 입력 계수가 정수 라고 가정하십시오 . 전력의 순서가 증가하거나 감소 할 수 있습니다.

  2. 입력 값이 2도 다항식 이라고 가정합니다 . 다항식에 정수 솔루션이없는 경우 아무 것도 반환 할 수 있습니다.

  3. 최종 결과는 정수만 가정합니다.

  4. 어떤 순서로도 결과를 인쇄 할 수 있습니다. 입력 다항식의 정도는 5보다 크지 않으므로 코드에서 처리 할 수 ​​있습니다.

  5. x의 해가 안장 점이되지 않도록 입력이 유효합니다.

또한 미분법으로 강제하지 않아도됩니다. 원하는 느낌의 방법을 사용할 수 있습니다.

샘플 입력 및 출력

[2,-8,0] -> (-8)
[2,3,-36,10] -> (91,-34)
[1,-8,22,-24,8] -> (-1,0,-1) 
[1,0,0] -> (0)

채점

이것은 이므로 가장 짧은 코드가 승리합니다.


1
내가 올바르게 이해한다면 : 예제에서 " 방정식 풀기 " 단계 는 부분적으로 당신의 이전 도전이 입니까? 또한, 공정은 " 이제 함수 X = 3이고, x = 5 바꾸어 수단 일본어"에서 함수 " 기능 "이 아닌 "의 기능 유도체를 오른쪽"?
Kevin Cruijssen

1
샘플 I / O 3의 경우, 나는 (-1, 0, 1)실제 정답이라고 생각합니다.하지만 확실하지 않습니다. 당신이 채팅에 저를 핑하는 데 동의하지 않는 경우.
HyperNeutrino

1
The input will be valid so that the solutions of x are not saddle points이 사건 [1,0,0,3]은 안 장점을주는 것으로 보인다.
정환 민

1
@JungHwanMin 아 규칙이 만들어지기 전에 예제가 추가되었습니다. 지금 제거되었습니다.
Manish Kundu

1
x^3 - 12x^2 + 45x + 8 = 0 , 비록 개인적으로 나는 그것을 f(x)=x^3-12x^2+45x+8쓰지 않고 그것을 선호합니다 . =0왜냐하면 =0우리가 방정식을 풀지 않고 함수를 다루기 때문에 의미가 없기 때문 입니다.
Weijun Zhou

답변:


4

젤리 , 20 바이트

ASŒRḅ@Ðḟ
J’U×µṖÇḅ@€³

온라인으로 사용해보십시오!

설명

ASŒRḅ@Ðḟ     Helper Function; find all integer solutions to a polynomial
             All integer roots are within the symmetric range of the sum of the absolute values of the coefficients
A            Absolute Value (Of Each)
 S           Sum
  ŒR         Symmetric Range; `n -> [-n, n]`
      Ðḟ     Filter; keep elements where the result is falsy for:
    ḅ@       Base conversion, which acts like the application of the polynomial
J’U×µṖÇḅ@€³  Main Link
J                             Range of length
 ’                    Lowered
  U          Reversed
   ×         Multiplied with the original list (last value is 0)
    µ        Begin new monadic chain
     Ṗ       Pop; all but the last element
      Ç      Apply last link (get all integer solutions of the derivative)
       ḅ@€³  Base conversion of the polynomial into each of the solutions; apply polynomial to each solution of the derivative.

이 프로그램의 도우미 함수 씨 Xcoder의 대답에서 찍은 여기 루이스의 대답의 기반으로하고 여기에


@JungHwanMin 나는 그것을 OP로 지적 할 것이다. 다항식의 미분 값이이므로 안장 점이 없다는 진술을 직접 위반 한 것 3입니다 0. 편집 오 당신은 이미 nvm 그냥 의견을 upvoted했다
HyperNeutrino

3

자바 스크립트 (ES7), 129 120 바이트

거듭 제곱의 순서로 계수를 취합니다.

a=>(g=x=>x+k?(A=g(x-1),h=e=>a.reduce((s,n,i)=>s+n*(e||i&&i--)*x**i,0))()?A:[h(1),...A]:[])(k=Math.max(...a.map(n=>n*n)))

테스트 사례

댓글

a => (                        // given the input array a[]
  g = x =>                    // g = recursive function checking whether x is a solution
    x + k ? (                 //   if x != -k:
      A = g(x - 1),           //     A[] = result of a recursive call with x - 1
      h = e =>                //     h = function evaluating the polynomial:
        a.reduce((s, n, i) => //       for each coefficient n at position i:
          s +                 //         add to s
          n                   //         the coefficient multiplied by
          * (e || i && i--)   //         either 1 (if e = 1) or i (if e is undefined)
          * x**i,             //         multiplied by x**i or x**(i-1)
          0                   //         initial value of s
        )                     //       end of reduce()
      )() ?                   //     if h() is non-zero:
        A                     //       just return A[]
      :                       //     else:
        [h(1), ...A]          //       prepend h(1) to A[]
    :                         //   else:
      []                      //     stop recursion
  )(k = Math.max(             // initial call to g() with x = k = maximum of
    ...a.map(n => n * n)      // the squared coefficients of the polynomial
  ))                          // (Math.abs would be more efficient, but longer)

1
실패 0,0,1(x ^ 2 = 0)
betseg

@betseg 신고 해 주셔서 감사합니다. 결정된.
Arnauld

3

Julia 0.6 ( Polynomials패키지 포함), 57 바이트

using Polynomials
x->map(Poly(x),roots(polyder(Poly(x))))

온라인으로 사용해보십시오!

계수를 증가하는 순서대로 취합니다. 즉, 첫 번째 입력은 상수 항입니다.

예제 실행 :

julia> using Polynomials

julia> g = x -> map(Poly(x), roots(polyder(Poly(x))))
(::#1) (generic function with 1 method)

julia> g([8,45,-12,1])
2-element Array{Float64,1}:
 58.0
 62.0

3

자바 (8) 364 239 227 226 218 바이트

a->{int l=a.length,A[]=a.clone(),s=0,i,r,f=l,p;for(;f>0;A[--f]*=f);for(int n:A)s+=n<0?-n:n;for(r=~s;r++<s;){for(p=0,i=f=1;i<l;f*=r)p+=A[i++]*f;if(p==0){for(f=i=0;i<l;f+=a[i++]*Math.pow(r,p++));System.out.println(f);}}}

이 대답과 동일한 기능을 사용합니다.

@ OlivierGrégoire 덕분에 배열을 역순으로하여 -8 바이트 .

설명:

온라인으로 사용해보십시오.

a->{                  // Method with integer-varargs parameter and integer return-type
  int l=a.length,     //  The length of the input-array
      A[]=a.clone(),  //  Copy of the input-array
      s=0,            //  Sum-integer, starting at 0
      i,              //  Index-integer
      r,              //  Range-integer
      f=l,            //  Factor-integer, starting at `l`
      p;              //  Polynomial-integer
  for(;f>0;           //  Loop over the copy-array
    A[--f]*=f);       //   And multiply each value with it's index
                      //   (i.e. [8,45,-12,1] becomes [0,45,-24,3])
  for(int n:A)        //  Loop over this copy-array:
    s+=n<0?-n:n;      //   And sum their absolute values
  for(r=~s;r++<s;){   //  Loop `r` from `-s` up to `s` (inclusive) (where `s` is the sum)
    for(p=0,          //   Reset `p` to 0
        i=f=1;        //   and `f` to 1
                      //   (`i` is 1 to skip the first item in the copy-array)
        i<l;          //   Inner loop over the input again, this time with index (`i`)
        f*=r)         //     After every iteration: multiply `f` with the current `r`
      p+=             //    Sum the Polynomial-integer `p` with:
         A[i++]       //     The value of the input at index `i`,
               *f;}   //     multiplied with the current factor `f`
    if(p==0){         //   If `p` is now 0:
      for(f=i=0;      //    Use `f` as sum, and reset it to 0
          i<l;        //    Loop over the input-array
        f+=a[i++]*Math.pow(r,p++));
                      //     Fill in `r` in the parts of the input-function
      System.out.println(f);}}}
                      //    And print the sum

2
실패 1,0,0(x ^ 2 = 0)
betseg

@betseg 감사합니다! 고정 및 골프.
Kevin Cruijssen

1
다음과 같이 개수를 줄이려면 역순으로 입력을 수락해야합니다 (명시 적으로 허용됨) int... ,i, ...; for(;f>0;)A[--f]*=f;. 내가 실수하지 않는 한, 이것은 적어도 4 바이트를 절약해야합니다. 이렇게하면 입력에 대한 모든 액세스 권한을 반전시켜야합니다.
Olivier Grégoire

@ OlivierGrégoire 감사합니다. 8 바이트가 절약되었습니다!
Kevin Cruijssen





당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.