Propriedades de funções binárias


14

Muitos tópicos importantes na álgebra abstrata envolvem uma função binária atuando em um conjunto. Várias propriedades de tais funções foram definidas na investigação de tais tópicos.

Seu desafio será determinar se uma determinada função binária em um determinado domínio possui cinco dessas propriedades.

Propriedades

Fecho

Uma função binária é fechada se todas as saídas possíveis estiverem no domínio.

Associatividade

Uma função binária é associativa se a ordem na qual a função é aplicada a uma série de entradas não afeta o resultado. Ou seja, $é associativo, se (a $ b) $ csempre igual a $ (b $ c). Observe que, já que o valor(a $ b) é usado como entrada, as funções associativas devem ser fechadas.

Comutatividade

Uma função binária é comutativa se a troca da ordem das entradas não alterar o resultado. Em outras palavras, se a $ bsempre é igual b $ a.

Identidade

Uma função binária possui um elemento de identidade se existir algum elemento eno domínio, como a $ e = a = e $ apara todos ano domínio.

Idempotência

Uma função binária é idempotente se aplicá-la a duas entradas idênticas fornecer esse número como saída. Em outras palavras, se for a $ a = apara todos ano domínio.

Entrada

Você receberá uma função na forma de uma matriz, e o domínio da função serão os números 0 ... n-1, onde né o comprimento lateral da matriz.

O valor (a $ b)é codificado na matriz como o elemento th ada linha bth. Se a matriz de entrada for Q, então a $ b=Q[a][b]

Por exemplo, a função de exponenciação ( **em Python) no domínio [0, 1, 2]é codificada como:

[[1, 0, 0]
 [1, 1, 1]
 [1, 2, 4]]

Os domínios esquerdo e direito são os mesmos, portanto a matriz sempre será quadrada.

Você pode usar qualquer formato de matriz conveniente como entrada, como uma lista de listas, uma única lista em ordem de linhas ou colunas, o objeto de matriz nativa do seu idioma, etc. No entanto, você não pode executar uma função diretamente como entrada.

Para simplificar, todas as entradas da matriz serão inteiras. Você pode assumir que eles se encaixam no tipo inteiro nativo do seu idioma.

Resultado

Você pode indicar quais das propriedades acima estão em qualquer formato que escolher, incluindo uma lista de booleanos, uma sequência com um caractere diferente para cada propriedade etc. No entanto, deve haver uma saída distinta e exclusiva para cada um dos 24 subconjuntos possíveis das propriedades. Essa saída deve ser facilmente legível por humanos.

Exemplos

A função máxima no domínio n = 4:

[[0, 1, 2, 3]
 [1, 1, 2, 3]
 [2, 2, 2, 3]
 [3, 3, 3, 3]]

Essa função possui as propriedades de fechamento, associatividade, comutatividade, identidade e idempotência.

A função de exponenciação no domínio n = 3:

[[1, 0, 0]
 [1, 1, 1]
 [1, 2, 4]]

Esta função não possui nenhuma das propriedades acima.

A função de adição no domínio n = 3:

[[0, 1, 2]
 [1, 2, 3]
 [2, 3, 4]]

Essa função tem as propriedades de comutatividade e identidade.

O combinador K no domínio n = 3:

[[0, 0, 0]
 [1, 1, 1]
 [2, 2, 2]]

Esta função possui as propriedades de fechamento, associatividade e idempotência.

A função de diferença absoluta no domínio n = 3:

[[0, 1, 2]
 [1, 0, 1]
 [2, 1, 0]]

Esta função tem as propriedades de fechamento, comutatividade e identidade.

A função média, arredondando para par, no domínio n = 3:

[[0, 0, 1]
 [0, 1, 2]
 [1, 2, 2]]

Esta função possui as propriedades de fechamento, comutatividade, identidade e idempotência.

A função de igualdade no domínio n = 3:

[[1, 0, 0]
 [0, 1, 0]
 [0, 0, 1]]

Esta função tem as propriedades de fechamento e comutatividade.

Desafio

Isso é código de golfe. Aplicam-se brechas padrão . Menos bytes ganham.

Respostas:


4

Pitão, 51 bytes

[qKUQ@VQKCIQ}]Km{@RdCBQKJ!-sQK&JqF.bsm@L@QdYN.p,sQK

Experimente on-line: Demonstration or Test Suite

Isso imprime uma lista de 5 valores booleanos. Eles indicam as propriedades na ordem:

[Idempotence, Commutativity, Identity, Closure, Associativity]

Aqui está um formato de saída melhor: Demonstration or Test Suite

Explicação:

Idempotência:

qKUQ@VQK
   Q       Q = input matrix
  UQ       [0, 1, ..., len(matrix)-1]
 K         assign to K
    @VQK   vectorized lookup of Q and K //gets the diagonal elements
qK         check, if this is equal to K

Comutatividade:

CIQ   check if transpose(Q) is equal to Q

Identidade:

}]Km{@RdCBQK
   m       K   map each d in K to:
        CBQ       the list [Q, transpose(Q)]
     @Rd          take the d-th element of each ^
    {             remove duplicates
}]K            check if [K] is in ^

Fecho:

J!-sQK
   sQ    sum(Q) //all elements of Q
  -  K   remove the elements, that also appear in K
 !       ckeck, if the results in an empty list
J        store the result in J

Associatividade:

&JqF.bsm@L@QdYN.p,sQK
               .p,sQK  all permutations of [sum(Q), K] //all 2 ;-)
    .b                 map each pair (N,Y) of ^ to:
       m      N           map each d of N to:
          @Qd                the row Q[d]
        @L   Y               map each element of Y to the corr. element in ^
      s                   unfold this 2-d list
  qF                   check if they result in identically lists
&J                     and J

5

Haskell, 178 171 bytes

import Data.List
f x=[c,c&&and[(m%n)%o==m%(n%o)|m<-b,n<-b,o<-b],x==t,all(elem b)[x,t],b==[i%i|i<-b]]where c=all(l>)(id=<<x);b=[0..l-1];a%b=x!!a!!b;l=length x;t=transpose x

Retorna uma lista com cinco booleanos, que estão em fechamento de ordem, associatividade, comutatividade, identidade e idempotência.

Exemplo de uso: f [[1, 0, 0],[0, 1, 0],[0, 0, 1]]-> [True,False,True,False,False].

Como funciona:

f x=[
  c,                         -- closure (see below)
  c&&and[(m%n)%o==m%(n%o)|   -- assoc: make sure it's closed, then check the
          m<-b,n<-b,o<-b],   --        assoc rule for all possible combinations
  x==t,                      -- comm: x must equal it's transposition
  all(elem b)[x,t],          -- identity: b must be a row and a column
  b==[i%i|i<-b]              -- idemp: element at (i,i) must equal i
  ]
  where                      -- some helper functions
  c=all(l>)(id=<<x);         -- closure: all elements of the input must be < l 
  b=[0..l-1];                -- a list with the numbers from 0 to l-1
  a%b=x!!a!!b;               -- % is an access function for index (a,b)
  l=length x;                -- l is the number of rows of the input matrix
  t=transpose x

Edite @xnor encontrou alguns bytes para salvar. Obrigado!


Que tal c=all(l>)?
Xnor

Também [i%i|i<-b]==b.
Xnor

Muito legível para o código de golfe - bom!
Isaacg

4

CJam, 95 bytes

q~:Ae_A,:Bf<:*'**B3m*{_{A==}*\W%{Az==}*=}%:*'A*A_z='C*B{aB*ee_Wf%+{A==}f*B,2*='1*}%Ae_B)%B,='I*

Imprime uma subsequência de *AC1I. *é o símbolo para o fechamento , Aé para associativo , Cé para comutativo , 1é para identidade e Ié para idempotente .


A matriz de entrada é lida q~e armazenada em A (:A ).

Fecho

Ae_A,:Bf<:*'**

Se todos os :*elementos ( ) na matriz ( Ae_) forem menores f<que B = tamanho (A) ( A,:B), imprima um *('** ).

Associatividade

B3m*{_{A==}*\W%{Az==}*=}%:*'A*

Gere todos os triplos no domínio ( B3m*). Imprimimos Ase todos eles satisfizerem uma condição ( {...}%:*'A*).

A condição é que, para alguns triplos [i j k], dobre à esquerda essa lista com A ( _{A==}*) e dobre à esquerda seu reverso [k j i]( \W%) com A op ( {Az==}*), a versão invertida de Aé igual (= ).

Comutatividade

Um deve ser igual a sua transposta: A_z=. Nesse caso, imprimimos C('C= ).

Identidade

B{                         }%   For each element X in the domain (0..N-1):
  aB*                           Make N copies.
     ee                         [[0 X] [1 X] ...]
       _Wf%+                    [[0 X] [1 X] ... [X 0] [X 1] ...]
            {A==}f*             [A(0, X) A(1, X) ... A(X, 0) A(X, 1)]
                   B,2*=        This list should equal the domain list repeated twice.
                        '1*     If so, X is an identity: print a 1.

A identidade é necessariamente única, portanto, podemos imprimir apenas uma 1 .

Idempotente

Ae_B)%B,='I*

Verifique se a diagonal é igual B,. Nesse caso, imprima uma I.


3

Matlab, 226

a=input('');n=size(a,1);v=1:n;c=all(0<=a(:)&a(:)<n);A=c;for i=v;for j=v(1:n*c);for k=v(1:n*c);A=A&a(a(i,j)+1,k)==a(i,a(j,k)+1);end;end;b(i)=all(a(i,:)==v-1 & a(:,i)'==v-1);end;disp([c,A,~norm(a-a'),any(b),all(diag(a)'==v-1)])

Uma coisa importante a se notar é que não-fechado implica não-associativo. Muitas dessas propriedades podem ser facilmente verificadas usando algumas propriedades da matriz:

  • Encerramento : todas as entradas da matriz no intervalo especificado?
  • Associatividade : Como sempre, a mais difícil de verificar
  • Comutatividade : a matriz é simétrica?
  • Identidade : Existe um índice k tal que a k-ésima linha e a k-ésima coluna sejam exatamente a lista dos índices?
  • Idempotência : a diagonal corresponde à lista de índices?

Entrada via notação padrão do Matlab: [a,b;c,d]ou [[a,b];[c,d]]ou [a b;c d]etc

Saída é um vetor de zeros, 1 = verdadeiro, 0 = falso, para cada uma das propriedades na ordem especificada.

Código completo:

a=input('');
n=size(a,1);
v=1:n;
c=all(0<=a(:)&a(:)<n);               %check for closedness
A=c;
for i=v;
   for j=v(1:n*c); 
      for k=v(1:n*c);
          A=A&a(a(i,j)+1,k)==a(i,a(j,k)+1);   %check for associativity (only if closed)
      end;
   end;
   b(i)=all(a(i,:)==v-1 & a(:,i)'==v-1);      %check for commutativity
end
%closure, assoc, commut, identity, idempotence
disp([c,A,~norm(a-a'),any(b),all(diag(a)'==v-1)]);

3

JavaScript (ES6) 165

Uma função anônima que retorna uma matriz com cinco valores 0/1, que estão na ordem Encerramento, Associatividade, Comutatividade, Identidade e Idempotência.

q=>q.map((p,i)=>(p.map((v,j)=>(w=q[j][i],v-w?h=C=0:v-j?h=0:0,q[v]?A&=!q[v].some((v,k)=>v-q[i][q[j][k]]):A=K=0),h=1,p[i]-i?P=0:0),h?I=1:0),A=P=K=C=1,I=0)&&[K,A,C,I,P]

Menos golfe

f=q=>(
  // A associativity, P idempotence, K closure, C commuativity
  // assumed true until proved false
  A=P=K=C=1, 
  I=0, // Identity assumed false until an identity element is found
  q.map((p,i)=> (
      h=1, // assume current i is identity until proved false
      p[i]-i? P=0 :0, // not idempotent if q[i][i]!=i for any i
      p.map((v,j)=> (
          w=q[j][i], // and v is q[i][j]
          v-w // check if q[j][i] != q[i][j]
          ? h=C=0 // if so, not commutative and i is not identity element too
          : v-j // else, check again for identity
            ? h=0 // i is not identity element if v!=j or w!=j
            : 0,
          q[v] // check if q[i][j] in domain
            ? A&=!q[v].some((v,k)=>v-q[i][q[j][k]]) // loop for associativity check
            : A=K=0 // q[i][j] out of domain, not close and not associative
        )
      ),
      h ? I=1 : 0 // if i is the identity element the identity = true
    )
  ),
  [K,A,C,I,P] // return all as an array
)

Teste

f=q=>
  q.map((p,i)=>(
    p.map((v,j)=>(
      w=q[j][i],
      v-w?h=C=0:v-j?h=0:0,
      q[v]?A&=!q[v].some((v,k)=>v-q[i][q[j][k]]):A=K=0
    ),h=1,p[i]-i?P=0:0),
    h?I=1:0
  ),A=P=K=C=1,I=0)
  &&[K,A,C,I,P]

// test

console.log=x=>O.textContent+=x+'\n';

T=[
 [
  [[0, 1, 2, 3],
   [1, 1, 2, 3],
   [2, 2, 2, 3],
   [3, 3, 3, 3]]
 ,[1,1,1,1,1]] // has the properties of closure, associativity, commutativity, identity and idempotence.
,[ // exponentiation function on domain n=3:
  [[1, 0, 0],
   [1, 1, 1],
   [1, 2, 4]]
 ,[0,0,0,0,0]] // has none of the above properties.
,[ // addition function on domain n=3:
  [[0, 1, 2],
   [1, 2, 3],
   [2, 3, 4]] 
 ,[0,0,1,1,0]] // has the properties of commutativity and identity.
,[ // K combinator on domain n=3:
  [[0, 0, 0],
   [1, 1, 1],
   [2, 2, 2]]
 ,[1,1,0,0,1]] // has the properties of closure, associativity and idempotence.
,[ // absolute difference function on domain n=3:
  [[0, 1, 2],
   [1, 0, 1],
   [2, 1, 0]]
 ,[1,0,1,1,0]] // has the properties of closure, commutativity and identity.
,[ // average function, rounding towards even, on domain n=3:
  [[0, 0, 1],
   [0, 1, 2],
   [1, 2, 2]]
 ,[1,0,1,1,1]] // has the properties of closure, commutativity, identity and idempotence.
,[ // equality function on domain n=3:
  [[1, 0, 0],
   [0, 1, 0],
   [0, 0, 1]]
 ,[1,0,1,0,0]] // has the properties of closure, commutativity,
]  

T.forEach(t=>{
  F=t[0],X=t[1]+'',R=f(F)+'',console.log(F.join`\n`+'\n'+R+' (expected '+X+') '+(X==R?'OK\n':'Fail\n'))
  })
<pre id=O></pre>

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.