Um exercício de aquecimento escolar para ocupar seu tempo - página 5

 
Aleksey Nikolayev:

1) É difícil provar que os vértices da área máxima devem estar no mesmo círculo (teorema de Cramer). Eu não sei como provar ou onde ler a prova.

2) Eu não acredito realmente na existência de fórmula analítica para a área máxima ou raio de um círculo.

3) A soma dos elementos da matriz pode ser calculada por MathSum()

1) Penso que este é um fato óbvio. E é fácil provar, entendendo que a área máxima de um triângulo com um dado vértice A, linha média h e dado lado oposto a é a área de um triângulo isósceles, quando o ângulo no vértice dado é o máximo. E a área de tal triângulo é h*a/2

Imagine que todos os nós entre determinados lados de polígonos são flexíveis (como em um conjunto de construção infantil sobre ímãs) e é claro que podemos organizar os lados de tal forma que todos os vértices tenham um centro equidistante comum (desde que o lado maior seja menor do que a soma dos outros lados, caso contrário eles não podem ser conectados), ou seja, eles estão inscritos em um círculo. E esta será a área máxima, pois consiste na soma das áreas de triângulos isósceles, com um lado igual ao raio deste círculo.

2) Eu acredito que

3) Eu não encontrei tal fórmula em MQL4 ou MQL5

 
Nikolai Semko:

1) Penso que este é um fato óbvio.

intuitivamente sim, mas não se estende a uma prova rígida por nenhum trecho.

2) Eu acredito que

Se houvesse uma, ela poderia ser encontrada, há apenas um sistema de equações

Aleksey Nikolayev:

1) A dificuldade está em provar que os vértices do mnc com a área máxima devem estar no mesmo círculo (teorema de Cramer). Eu não sei como provar ou onde ler a prova.

Eu não encontrei tal teorema, apenas referências a esta propriedade.

Como sempre, referências inúteis e nenhuma palavra sobre o assunto.

 
Andrei Trukhanovich:


como de costume referências inúteis e não uma palavra de substância.

é realmente inútil para você

 
Nikolai Semko:

1) Penso que este é um fato óbvio. E é facilmente comprovado pelo entendimento de que a área máxima de um triângulo com um dado vértice A, linha média h e dado lado oposto a é a área de um triângulo isósceles quando o ângulo no vértice dado é o máximo. E a área de tal triângulo é h*a/2

Imagine que todos os nós entre determinados lados de polígonos são flexíveis (como em um conjunto de construção infantil sobre ímãs) e é claro que podemos organizar os lados de tal forma que todos os vértices tenham um centro equidistante comum (desde que o lado maior seja menor do que a soma dos outros lados, caso contrário eles não podem ser conectados), ou seja, inscritos em um círculo. E esta será a área máxima, pois consiste na soma das áreas de triângulos isósceles, com um lado igual ao raio deste círculo.

2) Eu acredito que

3) Eu não encontrei tal fórmula em MQL4 ou MQL5.

1) Talvez possa ser de alguma forma formalizada como igualdade a zero de variação (derivada) da área de um mnc por coordenadas de vértices quando estes se encontram em um círculo. Somente esta é uma condição de extremismo local e precisamos provar 1) que é uma condição máxima e 2) que é global.

3) Soma Matemática()

#include <Math\Stat\Math.mqh>
void OnStart()
{
  double a[] = {1.0, 2.0, 3.0}, s;
  s = MathSum(a);
  Print("s=", s);
}

s=6.0



 

Você obtém um polinômio a partir das raízes dos outros polinômios, e de todo este baad over toma três derivados. Fórmulas quilométricas. E quem sabe, talvez haja uma surpresa à espera no final. Teremos que conseguir algum tipo de truque.

 
Andrei Trukhanovich:

intuitivamente sim, mas não se trata nem mesmo de uma prova rígida por nenhum trecho.

se houvesse uma, poderia ser encontrada, existe apenas um sistema de equações

Eu não consegui encontrar tal teorema, apenas menciona esta propriedade.

como de costume referências inúteis e nem uma única palavra sobre o assunto.

Buscando no Google "área máxima polígono dado lados", descobriu apenas que este resultado é "bem conhecido") e soluções numéricas como a dada por Nikolay.

Aparentemente, você tem que percorrer alguns livros antigos sobre geometria - hoje em dia eles não gostam de expor sobre tais coisas.

 

A solução acima só é válida para polígonos cujo centro da circunferência se encontra dentro do perímetro. Tente triângulo {2,2,3.9}

Em termos gerais (aproximação pelo dobro de precisão) é resolvido da seguinte forma:

enum EEqual {LESS=-1,EQUALY,MORE};
//-------------------------------------------------------
struct SRes{
   double s;
   double r;
   double degDelta;
   SRes(){ZeroMemory(this);}
   SRes(double _s,double _r,double _degDelta):s(_s),r(_r),degDelta(_degDelta){}
   SRes(const SRes &other) {this=other;}
   bool operator !() {return !s;}
};
//-------------------------------------------------------
const double _2PI=2*M_PI;
//-------------------------------------------------------
EEqual Check(double &array[],int size){
   int ii=0;
   double max=0.0,
          tmp=0.0,
          sum=0.0;
   for (int i=0;i<size;++i){
      if (array[i]<=0.0) return false;
      max=MathMax(max,array[i]);
      if (max!=tmp){
         ii=i;
         tmp=max;}
      sum+=array[i];}
   EEqual ret=max<sum/2?MORE:LESS;
   if (ret==MORE){
      tmp=array[ii];
      array[ii]=array[--size];
      array[size]=tmp;}
   return ret;}
//---------------------------------------------------
SRes ComputeCenterOut(const double &array[], double deg){
   int size=ArraySize(array)-1;
   double r=array[size]/2.0/sin((deg-M_PI)/2.0);
   double sum=0.0,
          square=-r*cos(deg/2.0)*array[size]/2.0;
   for (int i=0;i<size;++i){
      double _deg=2.0*MathArcsin(array[i]/2.0/r);
      sum+=_deg;
      square+=r*cos(_deg/2.0)*array[i];}
   return SRes(square,r,deg-M_PI-sum);
}
//---------------------------------------------------
SRes ComputeCenterIn(const double &array[], double deg){
   int size=ArraySize(array)-1;
   double r=array[size]/2.0/sin(deg/2.0);
   double sum=deg,
          square=r*cos(deg/2.0)*array[size]/2.0;
   for (int i=0;i<size;++i){
      double _deg=2.0*MathArcsin(array[i]/2.0/r);
      sum+=_deg;
      square+=r*cos(_deg/2.0)*array[i]/2.0;}
   return SRes(square,r,_2PI-sum);
}
//---------------------------------------------------
SRes ComputeSquare(const double &array[],double min,double max,SRes &prev){
   double a=(min+max)/2.0;
   if (a==min||a==max) return prev;
   SRes res=a>M_PI?ComputeCenterOut(array,a):ComputeCenterIn(array,a);
   if (res.degDelta==0.0||res.s==prev.s) return res;
   if (res.degDelta>0.0) min=a;
   else max=a;
   return ComputeSquare(array,min,max,res);}
//---------------------------------------------------
SRes Square(const double &in[]){
   double tmp[];
   int size=ArrayCopy(tmp,in);
   if (Check(tmp,size)!=MORE) return SRes();
   double aMax=_2PI,
          a=aMax/size;
   return ComputeSquare(tmp,a,aMax,SRes());
}

void OnStart(void)
{
   double arr[]={2,3.9,2};
   ulong time=GetMicrosecondCount();
   SRes res=Square(arr);
   time=GetMicrosecondCount()-time;
   if (!res) Print("Многоугольника с заданными сторонами не существует");
   else PrintFormat("Time=%lli %ss\n"
                    "Square=%f\n"
                    "Radii=%f",time,"\xB5",res.s,res.r);
}
 
Vladimir Simakov:

A solução acima só é válida para polígonos cujo centro da circunferência se encontra dentro do perímetro. Tente triângulo {2,2,3.9}

...

O que isso tem a ver com um triângulo se o problema é encontrar um polígono com a área máxima, dadas as dimensões dos lados?

 

Oops. Eu mesmo tenho apenas uma das variantes contando corretamente))))

UPD: Corrigido.

 
Dmitry Fedoseev:

Você obtém um polinômio a partir das raízes dos outros polinômios, e de todo este baad over toma três derivados. Fórmulas quilométricas. E quem sabe, talvez haja uma surpresa à espera no final. Teremos que conseguir algum tipo de truque.

Aqui está a função para a soma de todos os ângulos versus o raio. A área de solução de 2p é destacada em verde.

Talvez isto ajude.
Sou preguiçoso demais para abalar meus miolos, especialmente porque não sou muito bom na torre.

Arquivos anexados:
Zadacha2.mq5  4 kb