Ich möchte True
genau dann zurückkehren, wenn 3 von 4 booleschen Werten wahr sind.
Das nächste, was ich bekommen habe, ist (x ^ y) ^ (a ^ b)
:
Was soll ich machen?
boolean-logic
Simon Kuang
quelle
quelle
not a ^ not b ^ not c ^ not d
ist wahr, wenn genau einer der negierten Werte wahr ist. Dies bedeutet, dass von den ursprünglichen Werten genau einer falsch war.(!a&&b&&c&&d) || (a&&!b&&c&&d) || (a&&b&&!c&&d) || (a&&b&&c&&!d)
.Antworten:
Ich schlage vor, den Code so zu schreiben, dass er angibt, was Sie meinen. Wenn Sie möchten, dass 3 Werte wahr sind, erscheint es mir natürlich, dass der Wert 3 irgendwo erscheint.
Zum Beispiel in
C++
:Dies ist gut definiert in
C++
: Dasstandard (§4.7/4)
gibt an, dass die Konvertierungbool
inint
die erwarteten Werte 0 oder 1 ergibt.In Java und C # können Sie das folgende Konstrukt verwenden:
quelle
if (!!a + !!b + !!c + !!d == 3)
ist einfacher zu schreiben, obwohl ich nicht weiß, ob Compiler dies optimieren oder nicht# 1: Verwenden einer Verzweigung ?: 3 oder 4 Operationen
# 2 Nicht verzweigt, 7 Operationen
Als ich früher alles profilierte, stellte ich fest, dass nicht verzweigte Lösungen von Operation zu Operation viel schneller waren, da die CPU den Codepfad besser vorhersagen und mehr Operationen gleichzeitig ausführen konnte. Die Verzweigungsanweisung enthält hier jedoch etwa 50% weniger Arbeit.
quelle
Wenn dies Python gewesen wäre, hätte ich geschrieben
Oder
Oder
Oder
Oder
Oder
Oder
All dies funktioniert, da Boolesche Werte in Python Unterklassen von Ganzzahlen sind.
Oder, inspiriert von diesem tollen Trick ,
quelle
a=5;not not a == 1
. Der Nachteil, keinen echten Booleschen Typ zu haben.bool
:)Lange aber sehr einfache, (disjuntive) Normalform:
Es mag vereinfacht sein, aber das erfordert mehr Nachdenken: P.
quelle
(a & b & (c ^ d)) | ((a ^ b) & c & d)
?Ich bin mir nicht sicher, ob es einfacher ist, aber vielleicht.
((x xor y) and (a and b)) or ((x and y) and (a xor b))
quelle
Wenn Sie diese Logik in einer Programmiersprache verwenden möchten, ist mein Vorschlag
Oder wenn Sie möchten, können Sie all dies in eine einzige Zeile setzen:
Sie können dieses Problem auch auf Folgendes verallgemeinern
n of m
:quelle
Diese Antwort hängt vom Repräsentationssystem ab. Wenn jedoch 0 der einzige Wert ist, der als falsch interpretiert wird, und
not(false)
immer den gleichen numerischen Wert zurückgibt,not(a) + not(b) + not(c) + not(d) = not(0)
sollte dies der Trick sein.quelle
Denken Sie daran, dass die Antwort für Programmierfragen und nicht nur für logische Probleme offensichtlich von der Wahl einer Programmiersprache abhängt. Einige Sprachen unterstützen Funktionen, die für andere ungewöhnlich sind.
In C ++ können Sie beispielsweise Ihre Bedingungen testen mit:
Dies sollte der schnellste Weg sein, um Sprachen einzuchecken, die die automatische Konvertierung (auf niedriger Ebene) von booleschen zu ganzzahligen Typen unterstützen. Aber auch hier gibt es keine allgemeine Antwort auf dieses Problem.
quelle
Das Beste, was ich tun kann, ist
((x ^ y) ^ (a ^ b)) && ((a || x) && (b || y))
quelle
Der Faustausdruck sucht nach 1 oder 3
true
von 4. Der zweite eliminiert 0 oder 1 (und manchmal 2)true
von 4.quelle
Java 8, filtern Sie die falschen Werte heraus und zählen Sie die verbleibenden wahren Werte:
Dann können Sie es wie folgt verwenden:
Leicht verallgemeinert zu Überprüfung
n
vonm
Artikeln wahr.quelle
Um zumindest zu überprüfen, ob
n
alleBoolean
wahr sind (n muss kleiner oder gleich der Gesamtzahl vonBoolean
: p sein)Bearbeiten : Nach dem Kommentar von @ Cruncher
Um 3
boolean
von 4 zu überprüfenNoch einer :
((c & d) & (a ^ b)) | ((a & b) & (c ^ d))
( Details )quelle
Hier ist eine Möglichkeit, wie Sie es in C # mit LINQ lösen können:
quelle
Das ist die symmetrische Boolesche Funktion
S₃(4)
. Eine symmetrische Boolesche Funktion ist eine Boolesche Funktion, die nur von der Anzahl der eingestellten Eingaben abhängt, nicht jedoch von den Eingaben. Knuth erwähnt Funktionen dieses Typs in Abschnitt 7.1.2 in Band 4 der Kunst der Computerprogrammierung.S₃(4)
kann mit 7 Operationen wie folgt berechnet werden:Knuth zeigt, dass dies optimal ist, was bedeutet, dass Sie dies nicht in weniger als 7 Operationen mit den normalen Operatoren tun können:
&&, || , ^, <,
und>
.Wenn Sie dies jedoch in einer Sprache verwenden möchten, die
1
für wahr und0
für falsch verwendet wird, können Sie Addition auch einfach verwenden:das macht deine Absicht ganz klar.
quelle
Aus rein logischer Sicht habe ich mir das ausgedacht.
Wenn nach dem Taubenlochprinzip genau 3 wahr sind, dann sind entweder a und b wahr oder c und d sind wahr. Dann geht es nur noch darum, jeden dieser Fälle mit genau einem der anderen zu verbinden 2.
Wolfram Wahrheitstabelle
quelle
mine <=> his
dann weiß ich nicht, was ich sagen soll, da dies zu erwarten wäre.Wenn Sie ein Logikvisualisierungstool wie Karnaugh Maps verwenden, sehen Sie, dass dies ein Problem ist, bei dem Sie einen vollständigen Logikbegriff nicht vermeiden können, wenn Sie ihn in eine if (...) -Zeile schreiben möchten. Lopina hat es bereits gezeigt, es ist nicht möglich, es einfacher zu schreiben. Sie können ein wenig herausrechnen, aber es bleibt für Sie UND die Maschine schwer zu lesen.
Zähllösungen sind nicht schlecht und zeigen, wonach Sie wirklich suchen. Wie Sie effizient zählen, hängt von Ihrer Programmiersprache ab. Die Array-Lösungen mit Python oder LinQ sind schön anzusehen, aber Vorsicht, das ist LANGSAM. Wolfs (a + b + x + y) == 3 funktioniert gut und schnell, aber nur, wenn Ihre Sprache "wahr" mit 1 gleichsetzt. Wenn "wahr" durch -1 dargestellt wird, müssen Sie auf -3 testen: )
Wenn Ihre Sprache echte Boolesche Werte verwendet, können Sie versuchen, sie explizit zu programmieren (ich verwende! = Als XOR-Test):
"x! = y" funktioniert nur, wenn x, y vom booleschen Typ sind. Wenn es sich um einen anderen Typ handelt, bei dem 0 falsch und alles andere wahr ist, kann dies fehlschlagen. Verwenden Sie dann ein boolesches XOR oder ((bool) x! = (Bool) y) oder schreiben Sie "if (x) return (y == false) else return (y == true);", was etwas mehr ist Arbeit für den Computer.
Wenn Ihre Programmiersprache den Operator ternary ?: Bereitstellt, können Sie ihn auf kürzen
das hält ein bisschen Lesbarkeit, oder schneiden Sie es aggressiv auf
Dieser Code führt genau drei Logiktests durch (Zustand von a, Zustand von b, Vergleich von x und y) und sollte schneller sein als die meisten anderen Antworten hier. Aber du musst es kommentieren, sonst wirst du es nach 3 Monaten nicht verstehen :)
quelle
Hier gibt es viele gute Antworten; Hier ist eine alternative Formulierung, die noch niemand veröffentlicht hat:
quelle
Ähnlich wie bei der ersten Antwort, aber reines Java:
Ich ziehe es vor, sie als Ganzzahlen zu zählen, da dies zu besser lesbarem Code führt.
quelle
Verwenden Sie in Python Folgendes , um zu sehen, wie viele iterierbare Elemente True sind
sum
(ganz einfach):Konfiguration
Aktueller Test
Ausgabe
quelle
Wenn Sie nach der Lösung auf dem Papier (ohne Programmierung) suchen, sind K-Maps und Quine-McCluskey-Algorithmen genau das, wonach Sie suchen. Sie helfen Ihnen dabei, Ihre Boolesche Funktion zu minimieren.
In Ihrem Fall ist das Ergebnis
Wenn Sie dies programmgesteuert, mit einer nicht festgelegten Anzahl von Variablen und einem benutzerdefinierten "Schwellenwert" tun möchten, ist es ziemlich einfach und unkompliziert, einfach eine Liste von Booleschen Werten zu durchlaufen und das Auftreten von "true" zu zählen.
quelle
Angesichts der 4 booleschen Werte a, b, x, y wird diese Aufgabe in die folgende C-Anweisung übersetzt:
quelle
true
gleich 1 voraus . Dies ist nicht in allen Sprachen / Fällen wahr (kein Wortspiel beabsichtigt). blogs.msdn.com/b/oldnewthing/archive/2004/12/22/329884.aspxist was du willst. Grundsätzlich habe ich Ihren Code genommen und hinzugefügt, um zu überprüfen, ob tatsächlich 3 wahr und nicht 3 falsch sind.
quelle
Eine Programmierfrage ohne Antwort mit Rekursion? Undenkbar!
Es gibt genug "genau 3 von 4 Wahrheiten" -Antworten, aber hier ist eine verallgemeinerte (Java) Version für "genau m von n Wahrheiten" (sonst lohnt sich eine Rekursion nicht wirklich), nur weil Sie können:
Dies könnte mit so etwas wie bezeichnet werden:
was zurückkehren sollte
true
(weil 5 von 8 Werten wie erwartet wahr waren). Nicht ganz zufrieden mit den Wörtern "wahr" und "falsch", aber ich kann mir momentan keinen besseren Namen vorstellen ... Beachten Sie, dass die Rekursion stoppt, wenn zu vieletrue
oder zu vielefalse
Werte gefunden wurden.quelle
true
. Vielleicht so etwas wiecontainsNumberOfTrueValues()
. Nebenbei: Smalltalks Benennung wäre dafür allerdings viel besser geeignet :doesArray: someBooleans startingAt: anIndex containNumberOfTrueValues: anExpectedNumber foundSofar: aNumberFoundSoFar
. Wahrscheinlich zu lang für den Geschmack einiger Java-Entwickler, aber Smalltalker haben nie Angst vor der richtigen Benennung ;-)containsTruth
bedeutet wörtlich "enthält eine unbekannte Menge an Wahrheit", also glaube ich, dass es ganz in Ordnung ist.Da die Lesbarkeit ein großes Problem darstellt, können Sie einen beschreibenden Funktionsaufruf verwenden (um eine der vorgeschlagenen Implementierungen einzuschließen). Wenn diese Berechnung an mehreren Stellen durchgeführt werden muss, ist ein Funktionsaufruf der beste Weg, um eine Wiederverwendung zu erreichen, und macht deutlich, was Sie genau tun.
quelle
In PHP wird es dynamischer (nur für den Fall, dass Sie die Anzahl der Bedingungen usw. ändern):
quelle
Obwohl ich zeigen konnte, dass dies eine gute Lösung ist, ist Sam Hocevars Antwort später leicht zu schreiben und zu verstehen. In meinem Buch macht es das besser.
quelle
Hier ist ein C # -Code, den ich gerade geschrieben habe, weil Sie mich inspiriert haben:
Es braucht eine beliebige Anzahl von Argumenten und wird Ihnen sagen, ob n von ihnen wahr sind.
und du nennst es so:
So können Sie jetzt 7/9 oder 15/100 testen, wie Sie möchten.
quelle