Cette fonction devrait prendre quatre entrées de nombres entiers ( a
, b
, c
, d
) et retourner un mot binaire sur la base duquel les valeurs sont égales au maximum de quatre.
La valeur de retour sera comprise entre 1
et 0xF
.
Par exemple:
a = 6, b = 77, c = 1, d = 4
renvoie 2
(binaire 0010
; seul le deuxième bit de poids faible est défini, ce qui correspond à la b
seule valeur maximale)
a = 4, b = 5, c = 10, d = 10
renvoie 0xC
(binaire 1100
; 3e et 4e bits de poids faible définis correspondant à c
et d
égalant la valeur max)
a = 1, b = 1, c = 1, d = 1
renvoie 0xF
(binaire 1111
; les quatre bits sont définis car toutes les valeurs sont égales au maximum)
Voici une implémentation simple:
int getWord(int a, int b, int c, int d)
{
int max = a;
int word = 1;
if (b > max)
{
max = b;
word = 2;
}
else if (b == max)
{
word |= 2;
}
if (c > max)
{
max = c;
word = 4;
}
else if (c == max)
{
word |= 4;
}
if (d > max)
{
word = 8;
}
else if (d == max)
{
word |= 8;
}
return word;
}
la valeur de retour peut être une chaîne de 0 et de 1, un vecteur bool / bit ou un entier
Réponses:
Gelée , 2 octets
Prend l'entrée comme
[d,c,b,a]
. Renvoie une liste de booléens.Essayez-le en ligne!
Ṁ
M aximum=
égal à (implique que l'autre argument est l'argument d'origine; vectorise)la source
R , 17 octets
Essayez-le en ligne!
Renvoie un vecteur de booléens. Comme cette sortie a été confirmée, c'est préférable à la sortie numérique, car celle-ci est presque deux fois plus longue:
R , 33 octets
Essayez-le en ligne!
la source
APL (Dyalog Unicode) , 4 octets SBCS
Fonction de préfixe tacite anonyme. Prend
[a,b,c,d]
comme argument. Renvoie un tableau bit-booléen. *Essayez-le en ligne!
⌈/
Est-ce que le maximum de l'argument=
égal (vectorise)⌽
l'inverse de l'argument?* Notez qu'APL stocke des tableaux de booléens en utilisant un bit par valeur, donc cela retourne en effet un mot de 4 bits, malgré la forme d'affichage
0 0 1 0
.la source
Haskell ,
2018 octets2 octets économisés grâce au fier haskeller
Essayez-le en ligne!
la source
map
au lieu de(<$>)
serait deux octets plus court!Perl 6 , 12 octets
Essayez-le en ligne!
Bloc de code anonyme qui prend une liste d'entiers et renvoie une liste de booléens. Si nous devons renvoyer un nombre, c'est +4 octets pour envelopper l'intérieur du bloc de code avec
2:[...]
.Explication:
la source
Japt, 5
Essayez!
-4 octets grâce à @Oliver!
-2 octets grâce à @Shaggy!
L'entrée est un tableau à 4 éléments au format suivant:
La sortie est un tableau de bits.
la source
rw
conversion enr("w")
réduit en obtenant à plusieurs reprises le maximum. Même chose pourm¶
se convertirU.m("===", ...)
. Dans tous les cas, merci pour les conseils!Code machine x86 (MMX / SSE1), 26 octets (4x int16_t)
code machine x86 (SSE4.1), 28 octets (4x int32_t ou uint32_t)
code machine x86 (SSE2), 24 octets (4x float32) ou 27B vers cvt int32
(La dernière version qui convertit int32 en float n'est pas parfaitement précise pour les grands entiers qui arrondissent au même float. Avec l'entrée float, l'arrondi est le problème de l'appelant et cette fonction fonctionne correctement s'il n'y a pas de NaN, identifiant les flotteurs qui comparent == au maximum. Les versions entières fonctionnent pour toutes les entrées, les traitant comme des compléments signés 2.)
Tous ces éléments fonctionnent en mode 16/32/64 bits avec le même code machine.
Une convention d'appel stack-args permettrait de faire une boucle sur les arguments deux fois (trouver max puis comparer), ce qui pourrait nous donner une implémentation plus petite, mais je n'ai pas essayé cette approche.
x86 SIMD a vector-> bitmap entier comme une seule instruction (
pmovmskb
oumovmskps
ou pd), il était donc naturel pour cela même si les instructions MMX / SSE sont longues d'au moins 3 octets. Les instructions SSSE3 et ultérieures sont plus longues que SSE2 et les instructions MMX / SSE1 sont les plus courtes. Différentes versions depmax*
(vertical à nombres entiers compressés max) ont été introduites à des moments différents, SSE1 (pour les registres mmx) et SSE2 (pour les registres xmm) ayant uniquement un mot signé (16 bits) et un octet non signé.(
pshufw
etpmaxsw
sur les registres MMX sont nouveaux avec Katmai Pentium III, donc ils nécessitent vraiment SSE1, pas seulement le bit de fonctionnalité CPU MMX.)Cela peut être appelé à partir de C comme
unsigned max4_mmx(__m64)
avec l'i386 System V ABI, qui transmet un__m64
argumentmm0
. (Non x86-64 System V, qui passe__m64
enxmm0
!)S'il y avait un
pmovmskw
, ce qui aurait sauvé lepacksswb
et leand
(3 + 2 octets). Nous n'en avons pas besoinand eax, 0x0f
carpmovmskb
sur un registre MMX, les zéros supérieurs sont déjà zéros. Les registres MMX ne font que 8 octets de large, donc l'AL 8 bits couvre tous les bits non nuls possibles.Si nous savions que nos entrées n'étaient pas négatives, nous pourrions
packsswb mm1, mm0
produire des octets signés non négatifs dans les 4 octets supérieurs demm1
, en évitant le besoin d'and
afterpmovmskb
. Donc 24 octets.Le pack x86 avec saturation signée traite l'entrée et la sortie comme signées, donc il préserve toujours le bit de signe. ( https://www.felixcloutier.com/x86/packsswb:packssdw ). Fait amusant: le pack x86 avec saturation non signée traite toujours l' entrée comme signée. Cela pourrait être la raison pour laquelle il
PACKUSDW
n'a pas été introduit avant SSE4.1, alors que les 3 autres combinaisons de taille et de signature existaient depuis MMX / SSE2.Ou avec des entiers 32 bits dans un registre XMM (et
pshufd
au lieu depshufw
), chaque instruction aurait besoin d'un octet de préfixe de plus, sauf pourmovmskps
remplacer le pack / et. Maispmaxsd
/pmaxud
besoin d'un octet supplémentaire ...appelable à partir de C comme
unsigned max4_sse4(__m128i);
avec x86-64 System V, ou MSVC vectorcall (-Gv
), qui passent__m128i
/__m128d
/__m128
args dans les regs XMM commençant parxmm0
.Ou si nous acceptons la saisie en tant que
float
, nous pouvons utiliser les instructions SSE1. Lefloat
format peut représenter une large gamme de valeurs entières ...Ou si vous pensez que cela déforme trop les règles, commencez par un octet
0F 5B C0 cvtdq2ps xmm0, xmm0
à convertir, créant une fonction de 27 octets qui fonctionne pour tous les entiers qui sont exactement représentables en tant que binaire IEEE32float
, et de nombreuses combinaisons d'entrées où certaines entrées obtiennent arrondi à un multiple de 2, 4, 8 ou autre lors de la conversion. (Il est donc 1 octet plus petit que la version SSE4.1 et fonctionne sur n'importe quel x86-64 avec seulement SSE2.)Si l'une des entrées flottantes est NaN, notez qu'elle
maxps a,b
implémente exactement(a<b) ? a : b
, en gardant l'élément du 2e opérande non ordonné . Il pourrait donc être possible pour cela de retourner avec un bitmap non nul même si l'entrée contient du NaN, selon l'endroit où ils se trouvent.unsigned max4_sse2(__m128);
copier-mélanger avec
pshufd
est toujours notre meilleur pari:shufps dst,src,imm8
lit l'entrée pour la moitié inférieuredst
dedst
. Et nous avons besoin d'un copier-shuffle non destructif les deux fois, donc 3 octetsmovhlps
etunpckhps
/ pd sont tous les deux sortis. Si nous nous limitions à un maximum scalaire, nous pourrions les utiliser, mais cela coûte une autre instruction de diffuser avant de comparer si nous n'avons pas déjà le maximum dans tous les éléments.Connexes: SSE4.1
phminposuw
peut trouver la position et la valeur du minimumuint16_t
dans un registre XMM. Je ne pense pas que ce soit une victoire de soustraire de 65535 pour l'utiliser pour max, mais voir une réponse SO sur son utilisation pour max d'octets ou d'entiers signés.la source
Python 3.8 (version préliminaire) , 67 octets
Fonction lambda qui prend en 4 entiers, bit décale le résultat booléen de leur comparaison à la valeur maximale avec l'aide du nouvel opérateur d'affectation de Python 3.8 , et retourne le OU binaire des résultats
Essayez-le en ligne!
la source
Java (JDK) , 78 octets
Essayez-le en ligne!
[a,b,c,d]
.la source
05AB1E ,
32 octetsEntrée sous forme de liste de
[d,c,b,a]
, sortie sous forme de liste de booléens.Essayez-le en ligne ou vérifiez tous les cas de test .
Explication:
la source
JavaScript (ES6), 30 octets
Prend l'entrée comme
([d,c,b,a])
. Renvoie 4 valeurs booléennes.Essayez-le en ligne!
la source
Rubis ,
3422 octetsPrend l'entrée comme un tableau
[d, c, b, a]
et renvoie un tableau de 1 et de 0.Essayez-le en ligne!
la source
Python 3 ,
59 octets66 octetsEssayez-le en ligne!
Prend l'entrée en tant que
[a,b,c,d]
et génère une liste de booléens.Modifié pour être une fonction appropriée, puis enregistré 2 octets en supprimant les crochets autour du conditionnel.
la source
1. Python 3.5, 90 octets
Prend une séquence de nombres comme paramètres. Renvoie une chaîne "binaire"
exemple:
Explication
la source
C # (Visual C # Interactive Compiler) , 26 octets
Essayez-le en ligne!
Prend l'entrée au format
[d,c,b,a]
. Tous les autres ci-dessous prennent en compte[a,b,c,d]
C # (Visual C # Interactive Compiler) , 35 octets
Renvoie un
IEnumerable<bool>
.Essayez-le en ligne!
C # (Visual C # Interactive Compiler) , 39 octets
Renvoie un
IEnumerable<int>
, qui représente des bits.Essayez-le en ligne!
C # (Visual C # Interactive Compiler) , 49 octets
Imprime une chaîne binaire dans STDOUT.
Essayez-le en ligne!
la source
IEnumerable<bool>
est acceptable.PHP, 54 octets
ou
prendre l'entrée des arguments de ligne de commande. Courez avec
-nr
ou essayez-les en ligne .la source
Voici une version JS qui sort en binaire
mise à jour: plus courte avec jointure et sans recherche:
JavaScript (Node.js) , 42 octets
Essayez-le en ligne!
Précédent, avec recherche, 49 octets
Essayez-le en ligne!
Précédent, avec réduction, 52 octets:
Essayez-le en ligne!
la source
[0,1][...]
C # (Visual C # Interactive Compiler) , 51 octets
Essayez-le en ligne!
Ci-dessus est une fonction anonyme qui sort en modifiant un argument . La sortie est un tableau de 1 et de 0.
Vous trouverez ci-dessous une fonction récursive qui génère un entier.
C # (Visual C # Interactive Compiler) , 60 octets
Essayez-le en ligne!
Les deux fonctions prennent en entrée un tableau à 4 éléments.
la source
Python 2 , 35 octets
Essayez-le en ligne!
Prend la saisie dans le format [d, c, b, a] comme avec la réponse acceptée d' Adám donc je suppose que c'est OK.
Alternative pour 41 si ce n'est pas ...
Python 2 , 41 octets
Essayez-le en ligne!
la source
Python 3 , 42 octets
Renvoie simplement une liste indiquant si l'élément est le maximum pour chaque élément dans l'entrée. -2 octets si vous ne comptez pas l'
f=
affectation.Essayez-le en ligne!
la source
f=
ne compte que dans les fonctions récursivesLot, 92 octets
Prend les arguments comme paramètres de ligne de commande dans l'ordre inverse. Fonctionne en calculant arithmétiquement le maximum des paramètres en les réduisant et en ajoutant uniquement des différences positives par rapport au maximum en cours, puis en mappant à nouveau chaque paramètre cette fois en le comparant au maximum. De manière pratique,
cmd/cset/a
ne produit pas de nouvelle ligne, donc les résultats sont automatiquement concaténés ensemble. Le%f%
enregistre simplement 5 octets sur ce qui serait une construction répétée.la source