# Visible Dice Faces

A traditional Western die is a cube, on which the integers 1 to 6 are marked on the faces. Pairs that add to 7 are placed on opposite faces.

As it is cube, we can only see between 1 and 3 faces (inclusive)1 at any given time. Opposite faces can never be seen at the same time.

Your task is to write a program or function which, given a list of integers representing sides on a die, determines if it is possible to see these faces at the same time.

1Okay, maybe you can see 4 or 5 faces with a pair of eyes, but for the purpose of this challenge we observing the die from a single point.

# Rules:

• Your submission may assume the input list:
• Is non-empty.
• Only contains values which satisfy 1 ≤ n ≤ 6.
• Contains no duplicate elements.
• You may not assume that the input is sorted.
• Your submission should output a truthy / falsy value: truthy is the faces can be seen at the same time, falsy otherwise.
• This is , so the shortest answer (in bytes) wins!
• Standard loopholes are forbidden by default.

## Test Cases

Truthy:

[6]                 (One face)
[6, 2]              (Share a side)
[1, 3]              (Share a side)
[2, 1, 3]           (Share a vertex)
[3, 2, 6]           (Share a vertex)


Falsy:

[1, 6]              (1 and 6 are opposite)
[5, 4, 2]           (2 and 5 are opposite)
[3, 1, 4]           (3 and 4 are opposite)
[5, 4, 6, 2]        (Cannot see 4 faces)
[1, 2, 3, 4, 5, 6]  (Cannot see 6 faces)

• Commented Dec 4, 2017 at 20:30
• It seems that the last two falsey cases are superfluous as any list longer than 3 will contain opposing values, no? Commented Dec 6, 2017 at 12:22
• @WeckarE yes, obviously - if you have a look at the answers they all exploit this. It was just an easier explanation to write. Commented Dec 6, 2017 at 15:09
• You can still see up to 5 faces from a single point if you bent the light waves with something heavy like a black hole Commented Dec 14, 2017 at 6:46
• @Ferrybig So a mirror would be cheating, but a black hole is fair game? :-) Commented Mar 19, 2023 at 3:14

# JavaScript (ES6),  38 34 30 29  28 bytes

Takes input as any number of separate parameters. Returns 0 or 1.

(a,b,c,d)=>!(d|(a^b^c)%7)^!c


### Test cases

let f =

(a,b,c,d)=>!(d|(a^b^c)%7)^!c

console.log('[Truthy]')
console.log(f(6      ))
console.log(f(6, 2   ))
console.log(f(1, 3   ))
console.log(f(2, 1, 3))
console.log(f(3, 2, 6))

console.log('[Falsy]')
console.log(f(1, 6            ))
console.log(f(5, 4, 2         ))
console.log(f(3, 1, 4         ))
console.log(f(5, 4, 6, 2      ))
console.log(f(1, 2, 3, 4, 5, 6))

### How?

Below are simplified versions of the main expression according to the number of parameters provided, undefined variables being coerced to either 0 or false:

# of param. | simplified expression        | comment
------------+------------------------------+---------------------------------------------
1      | !(a % 7) ^ 1                 | always true
2      | !((a ^ b) % 7) ^ 1           | false for (1,6), (2,5) and (3,4)
3      | !((a ^ b ^ c) % 7)           | see the table below
4+     | !(d | (a ^ b ^ c) % 7)       | always false


NB: The order of (a,b,c) doesn't matter because they're always XOR'd together.

The trickiest case is the 3rd one. Here is a table showing all possible combinations:

a | b | c | a^b^c | %7 | =0? | faces that sum to 7
--+---+---+-------+----+-----+--------------------
1 | 2 | 3 |   0   |  0 | Yes | none
1 | 2 | 4 |   7   |  0 | Yes | none
1 | 2 | 5 |   6   |  6 | No  | 2 + 5
1 | 2 | 6 |   5   |  5 | No  | 1 + 6
1 | 3 | 4 |   6   |  6 | No  | 3 + 4
1 | 3 | 5 |   7   |  0 | Yes | none
1 | 3 | 6 |   4   |  4 | No  | 1 + 6
1 | 4 | 5 |   0   |  0 | Yes | none
1 | 4 | 6 |   3   |  3 | No  | 1 + 6
1 | 5 | 6 |   2   |  2 | No  | 1 + 6
2 | 3 | 4 |   5   |  5 | No  | 3 + 4
2 | 3 | 5 |   4   |  4 | No  | 2 + 5
2 | 3 | 6 |   7   |  0 | Yes | none
2 | 4 | 5 |   3   |  3 | No  | 2 + 5
2 | 4 | 6 |   0   |  0 | Yes | none
2 | 5 | 6 |   1   |  1 | No  | 2 + 5
3 | 4 | 5 |   2   |  2 | No  | 3 + 4
3 | 4 | 6 |   1   |  1 | No  | 3 + 4
3 | 5 | 6 |   0   |  0 | Yes | none
4 | 5 | 6 |   7   |  0 | Yes | none


# Alt. version #1, 32 bytes

Takes input as an array. Returns a boolean.

a=>a.every(x=>a.every(y=>x+y-7))


### Test cases

let f =

a=>a.every(x=>a.every(y=>x+y-7))

console.log('[Truthy]')
console.log(f([6]      ))
console.log(f([6, 2]   ))
console.log(f([1, 3]   ))
console.log(f([2, 1, 3]))
console.log(f([3, 2, 6]))

console.log('[Falsy]')
console.log(f([1, 6]            ))
console.log(f([5, 4, 2]         ))
console.log(f([3, 1, 4]         ))
console.log(f([5, 4, 6, 2]      ))
console.log(f([1, 2, 3, 4, 5, 6]))

# Alt. version #2, Chrome/Firefox, 34 bytes

This one abuses the sort methods of Chrome and Firefox. It doesn't work with Edge.

Takes input as an array. Returns 0 or 1.

a=>a.sort((a,b)=>k&=a+b!=7,k=1)&&k


### Test cases

let f =

a=>a.sort((a,b)=>k&=a+b!=7,k=1)&&k

console.log('[Truthy]')
console.log(f([6]      ))
console.log(f([6, 2]   ))
console.log(f([1, 3]   ))
console.log(f([2, 1, 3]))
console.log(f([3, 2, 6]))

console.log('[Falsy]')
console.log(f([1, 6]            ))
console.log(f([5, 4, 2]         ))
console.log(f([3, 1, 4]         ))
console.log(f([5, 4, 6, 2]      ))
console.log(f([1, 2, 3, 4, 5, 6]))

# Python 2, 35 bytes

lambda a:any(7-i in a for i in a)<1


Try it online!

• -1 byte in Python 3. Commented Dec 4, 2017 at 22:53
• @notjagan -1 more by replacing …<{1} with plain not… Commented Mar 21, 2023 at 17:16

-3 bytes thanks to H.PWiz.

f l=all(/=7)$(+)<$>l<*>l


Try it online!

## Explanation

f l=all(/=7)$(+)<$>l<*>l

f l=                      -- make a function f that takes a single argument l
(+)<$>l<*>l -- take the sum of each pair in the cartesian product... all(/=7)$             -- ...and check if they're all inequal to 7


# Regex (Perl / Java / PCRE2 v10.34+), 3029 27 bytes

^(?!.*:(x(\2?+:.*\b)?){7}:)


Takes its input in unary, as a concatenation of strings of x characters whose lengths represent the numbers, separated and enclosed on both sides by : characters. Example: :x:xxxxxx: represents [1, 6].

Try it online! - Perl
Try it online! - Java
Attempt This Online! - PCRE2 v10.40+

This is an adaptation of the 31 30 28 byte version below, but it prevents more than one split from occurring in a somewhat more complex manner. Upon matching a split, \2 captures the intervening elements, including commas – or just a single comma if there are no intervening elements.

How this prevents more than one split would be simple to explain if (?(2)\2) were used instead of \2?+. Then the mechanism would be that on subsequent attempts to match a splitting after one has already occurred, that would be forced to coincide with matching a duplicate element, or two commas in a row.

But \2?+ will successfully make an empty match if \2 is not an exact match at that position. However, note that if this did happen, it could only result in false negatives (returning "False" incorrectly) – never false positives – because it could make the pattern inside the negative lookahead match when it shouldn't, but it can't prevent a match that should have happened.

All lists of 4 or more numbers will return "False", so the addition of false negatives won't matter. And lists of 2 or fewer elements can only match one split anyway (where \2 captures a single comma alone), so no false negatives could result there.

So we only need to consider lists of 3 elements:

• Only two splits can occur at most, and if that is the case, \2 will contain exactly one comma. The first split prevents a second split from being matched because \2?+, would only match two commas in a row.
• Or if a split matches one intervening element, only one split can occur anyway, so there's no place for a second split to match.

And here is a test harness with all 156 lists of 3 or fewer elements, demonstrating this regex to work correctly:

Try it online! - Perl

# Regex (Perl / Java / Pythonregex / Ruby / PCRE), 3130 28 bytes

^(?!.*:(x\2?+(:).*\b|x){7}:)


Try it online! - Perl
Try it online! - Java
Try it online! / Attempt This Online! - Python (with regex)
Try it online! - Ruby
Try it online! - PCRE

This is an adaptation of the 33 32 31 29 byte version below, but it prevents more than one split from occurring with \2?+(,), which forces a split to coincide with matching two commas in a row (which can never happen in the input specification) if a split has already occurred.

# Regex (Perl / Boost / Python / Pythonregex / Ruby / PCRE / .NET), 333231 29 bytes

^(?!.*:(?(1)x|x(:.*\b)?){7}:)


Try it online! - Perl
Try it online! - Boost
Try it online! / Attempt This Online! - Python
Try it online! / Attempt This Online! - Python (with regex)
Try it online! - Ruby
Try it online! - PCRE
Try it online! - .NET

This works by asserting that no two numbers add up to exactly 7. It does this by consuming exactly 7 x characters – a split is allowed to occur at any point within this, but not more than once.

^             # Anchor to start
(?!           # Negative lookahead - assert that the following can't match:
# which denotes the beginning of a number's unary
# representation.
(?(1)         # Conditional upon whether \1 is set:
# If \1 is set:
x             # tail -= 1
|
# If \1 is unset:
# (This is only allowed to match once within this loop. There is no
# need to verify afterward that it matched exactly once, because the
# input specification allows us to assume there will be no numbers
# greater than 6 – so, 7 will never appear.)
x             # tail -= 1
(
:.*\b         # Complete the match for the current number, and
# unary representation.
)?            # Match the above optionally
){7}          # Iterate the above exactly 7 times; this can never result in
# the 7th iteration ending in a split, as that would require
# matching 7 x's in a row, but the input is guaranteed not to
# contain a 7.
:             # Assert that tail == 0 (i.e, that this is the end of a
# number's unary representation)
)


Strangely, this actually works with Python's re library, even though (?(2)...) is a forward-declared conditional, and re doesn't support forward-declared or nested backreferences; \2 in that position would throw an error.

Equally strangely, it works in Boost, even though that regex engine doesn't support nested or forward-declared backreferences either, and a \2 in that position would cause Boost to throw an error as well.

The previous 33 byte version did not work properly with Python's re; it used a nested conditional, and Python silently treated that as a no-op, making the regex return some false negatives. But strangely, that version works in Pythonregex, even though that engine doesn't support nested backreferences either.

# Regex (Perl / Java / Pythonregex / Ruby / PCRE / .NET), 343332 30 bytes

^(?!.*:(x(?!\2):.*\b()|x){7}:)


Try it online! - Perl
Try it online! - Java
Try it online! / Attempt This Online! - Python (with regex)
Try it online! - Ruby
Try it online! - PCRE
Try it online! - .NET

This adds Java support to the above 33 32 31 29 byte version, by removing the use of the conditional (?(2)...). Support for Python and Boost is dropped, due to the use of the nested backreference \2.

# Regex (ECMAScript 2018 / Pythonregex / .NET), 4136 34 bytes

^(?!(.*:)(\b(?<=^\1x+).*:x|x){7}:)


Try it online! - ECMAScript 2018
Try it online! / Attempt This Online! - Python (with regex)
Try it online! - .NET

^             # Anchor to start
(?!           # Negative lookahead - assert that the following can't match:
# which denotes the beginning of a number's unary
# representation;
# \1 = the entire portion of the string that has been
# skipped, going all the way back to its beginning.
(
\b            # Assert that we're on a word boundary
# The below is only allowed to match once within this loop. There is
# no need to verify afterward that it matched exactly once, because
# the input specification allows us to assume there will be no numbers
# greater than 6 (so, 7 will never appear).
(?<=          # Lookbehind - evaluated from right to left (so in this
# listing, read it from bottom to top)
^         # Assert this is the start of the string
\1        # Match \1
x+        # Skip back to the beginning of the unary representation
# of the current number
)
.*:           # Complete the match for the current number, and skip
# to the beginning of any subsequent number's unary
# representation.
x             # tail -= 1
|              # or...
x             # tail -= 1 (and do nothing else)
){7}          # Iterate the above exactly 7 times; this can never result in
# the 7th iteration ending in a split, as that would require
# matching 7 x's in a row, but the input is guaranteed not to
# contain a 7.
:             # Assert that tail == 0 (i.e, that this is the end of a
# number's unary representation)
)


A previous 41 byte version using lookbehind appears to expose a bug in Pythonregex:

^(?!(.*\b)x+(,.*\b)x+\b(?<=^\1(\2?x){7}))


Try it online! - ECMAScript 2018 - works
Attempt This Online! - Python (with regex) - does not work
Try it online! - .NET - works

Upon investigation, the bug actually has nothing to do with lookbehind. I reported it here and it is now fixed.

# Regex (ECMAScript or better), 736946414039 37 bytes

^(?!.*:(?=x*(.*))(x(?=\1).+\b|x){7}:)


Try it online! - ECMAScript (SpiderMonkey)
Try it online! - ECMAScript 2018 (Node.js)
Try it online! - Perl
Try it online! - Java
Try it online! - Boost
Try it online! - Python
Try it online! / Attempt This Online! - Python (with regex)
Try it online! - Ruby
Try it online! - PCRE
Try it online! - .NET

This now ports the 33 32 31 byte version's algorithm to support ECMAScript:

^             # Anchor to start
(?!           # Negative lookahead - assert that the following can't match:
# which denotes the beginning of a number's unary
# representation.
(?=x*(.*))    # \1 = the entire string following the current number's
#      unary representation
(
x             # tail -= 1
# The below is only allowed to match once within this loop. There is
# no need to verify afterward that it matched exactly once, because
# the input specification allows us to assume there will be no numbers
# greater than 6 (so, 7 will never appear).
(?=\1)        # Assert that the entire string following the current
# position matches what was captured in \1, which
# accomplishes two things – it asserts that we
# haven't skipped to another number yet, and that
# we've finished consuming the entire current number,
# i.e. that tail == 0.
# unary representation (the first character skipped
# will be a comma).
|              # or...
x             # tail -= 1 (and do nothing else)
){7}          # Iterate the above exactly 7 times; this can never result in
# the 7th iteration ending in a split, as that would require
# matching 7 x's in a row, but the input is guaranteed not to
# contain a 7.
\b            # Assert that tail == 0 (i.e, that this is the end of a
# number's unary representation)
)


The previous 73 69 byte version worked by treating every possible pair of numbers that add to 7 as a separate case, like the decimal version below:

^(?!(?=.*\bx\b).*x{6}|(?=.*\bxx\b).*\bx{5}\b|(?=.*\bxxx\b).*\bx{4}\b)


# Regex (.NET), 46 bytes

^(?!.*\b(){7}(?<-1>x)+,.*\b(?<-1>x)+(?(1)^)\b)


Obsoleted by the 33 32 byte version above.

# Regex (Perl / Boost / Python / Ruby / PCRE / .NET), 58 bytes

^(?!.*\b(x)?(xx)?(xxxx,.*\b|,.*\bxxxx)(?(2)|xx)(?(1)|x)\b)


Obsoleted by the versions above. Worked by capturing two numbers in binary, and asserting that the second number has all 3 of its lowermost bits flipped when compared to the first number (and asserting that this doesn't occur anywhere in the input).

# Regex (ECMAScript or better), 38 37 bytes

^(?!(?=.*1).*6|(?=.*2).*5|(?=.*3).*4)


Takes its input in decimal. There is no need for delimiters, because the full range fits into a single digit.

Try it online! - ECMAScript / Perl / Java / Python / .NET

Pure regex is very limited in what math can be done on decimal input, so this version just asserts that no two numbers occur anywhere in the list that add up to 7, by exhaustively listing all the pairs that could do so.

# Cubically, 41 34 bytes

$(7:*-!F-!S-!B'-!B'-!S-!F$):0+>2=%


Try it online!

Takes input as a space-separated list of integers, printing 1 for true and 0 for false.

Explanation:

$(7 ...$)


For every integer in the input...

:*


Place it in the notepad, and multiply it by itself.

Cubically can only use values in one of its nine memory locations, and the notepad is the only one that can be freely read or written, so I perform the next calculation "scaled up" by the current input value itself, memory location 7--since it's nonzero and doesn't change until we read a new integer (or character) with $ (or ~). This is shorter than using a face we don't modify as the scale factor, because the notepad is the implicit argument for * and the input is the implicit argument for -. -!F  Subtract the input from the notepad. If this makes it 0 (the original input was 1), rotate the front face of the memory Rubik's Cube once clockwise. Doing this once replaces a row of 0s on face 0 with 1; doing this again replaces those 1s with 5s. -!S-!B'-!B'-!S-!F  Repeat for the other five possible values: rotate the front if it's 6, the middle if it's 2 or 5, and the back if it's 3 or 4. (The back rotations have to be clockwise with respect to the front, so they're actually counterclockwise B' with respect to the back.) :0+>2  After the loop, set the notepad to the sum of face 0, add it to itself, and check if it's strictly greater than the sum of face 2. Face 0 contains a mix of 0, 1, and 5, and we want to discriminate between cases where it contains any 5s and cases where it doesn't. The greatest sum it can have without 5s is 9, and the least sum it can have with 5s is 15 (since only whole rows at a time are moved without being mixed, it has to be a multiple of 3), so doubling it turns 9 into 18, which is the sum of face 2 (since none of the rotations performed in the loop affected face 2). =%  Output whether or not the notepad equals the input buffer. The input buffer is set to 0 after exhausting the input, and the notepad contains 1 if the faces can't all be seen or 0 if they can, so comparing them for equality inverts that to satisfy the challenge's truthiness requirement. # APL (Dyalog), 7 bytes ~7∊∘.+⍨  Try it online! ∘.+⍨ - addition table (every element with every element) 7∊ - 7 exists? ~ - negate # APL (Dyalog), 7 bytes ⍬≡⊢∩7-⊢  Try it online! 7-⊢ - subtract each element from 7 ⊢∩ - intersect with the original array ⍬≡ - empty? # Mathematica, 20 bytes xFreeQ[#+x&/@x,7]  The  is \[Function] -12 bytes from Martin Ender -7 bytes from Misha Lavrov Try it online! # R, 27 bytes thanks to Gregor for fixing a bug function(d)!any((7-d)%in%d)  Try it online! Port of Chas Brown's answer. Having vectorized operations helps make this much shorter in R. • I think you need some parens around (7-d), other wise d%in%d takes precedence. Commented Dec 5, 2017 at 20:32 • @Gregor you're absolutely right. Commented Dec 5, 2017 at 20:35 # Retina, 21 20 bytes O. M1.*6|2.*5|34 0  Try it online! Link includes test cases. Edit: Saved 1 byte thanks to @MartinEnder. Explanation: O.  Sort the input. M1.*6|2.*5|34  Check for a pair of opposite sides (3 and 4 sort next to each other). This returns 1 for an invalid die or 0 for a valid one. 0  Logically negate the result. # Nibbles, 5.5 bytes (11 nibbles) -~+.$?@- 7


For each element x of input, checks tbat 7-x is not present in the input. Outputs 1 (truthy) if faces can be seen at the same time, and negative value (falsy) if they cannot.

-~+.$?@- 7 . # map over$       # input:
?      #   index of (or 0 if absent)
@     #   in input
#   of
- 7  #   7 minus
#   (implicit) each element
+         # sum the list
-~          # and subtract from 1.
# (0 and negative values are falsy,
# 1 is truthy)


# Nekomata + -e, 4 bytes

ᵒ+7f


Attempt This Online!

ᵒ+     Generate a 2d table with addition
7f   Check if the result is free of 7.


-e prints True if the computation has any result, and False otherwise.

Let's take [3,1,4] as an example. ᵒ+ returns the 2d array [[6,4,7],[4,2,5],[7,5,8]], which contains 7. So the result is False.

# ThunnoD, 7$$\5\log_{256}(96)\approx\$$ 4.12 bytes

7_Gze


Attempt This Online!

7_     # subtract each from 7
G    # map each to the input with it removed
ze  # all equal?


Now beating tied with the language's creator!

• Wow, you beat the language's creator! Commented Mar 18, 2023 at 2:41
• @Deadcode And all because of a weird interpreter thing--G is supposed to run on the whole array, but for some reason it vectorizes to each element which is why I have to check if all are equal instead of check if it is empty. Commented Mar 18, 2023 at 12:03
• @TheThonnu I think you implemented it incorrectly because its function doesn't really match its description... But it still came in handy here! Commented Mar 18, 2023 at 12:11
• @TheThonnu That's alright, competition is fun :) Especially when I win :P Commented Mar 18, 2023 at 12:17
• You're not winning any more :P Commented Mar 18, 2023 at 12:49

f x=null[1|7<-(+)<$>x<*>x]  Try it online! # Jelly, 5 bytes 7_f⁸Ṇ  Try it online! Port of Chas Brown's answer. ### Explanation 7_f⁸Ṇ 7_ Subtract each element from 7 f⁸ Filter with the original list Ṇ Check if empty  # Pyth, 5 bytes !@-L7  Try it here. • I could swear I tried this two minutes ago and it didn’t work... Huh I wonder what went wrong Commented Dec 4, 2017 at 21:04 • First thing I thought of? The Sandlot. Commented Dec 4, 2017 at 22:23 # Actually, 8 bytes ;∙♂Σ7@cY  Try it online! (runs all the test cases) Explanation: ;∙♂Σ7@cY ;∙ Cartesian product with self ♂Σ sum all pairs 7@c count 7s Y logical negate  ## Husk, 5 bytes Ëo≠7+  Try it online! ### Explanation Ëo Check that the following function gives a truthy value for all pairs from the input. + Their sum... ≠7 ...is not equal to 7.  # Perl 6, 18 bytes !(1&6|2&5|3&4∈*)  Try it online! 1 & 6 | 2 & 5 | 3 & 4 is a junction consisting of the numbers 1 and 6, OR the numbers 2 and 5, OR the numbers 3 and 4. This junction is an element of (∈) the input list * if it contains 1 and 6, or 2 and 5, or 3 and 4. That result is then negated (!) to get the required boolean value. # Vyxal, 4 bytes 7ε↔¬  Try it Online! Very simple answer, ports the approach of the 5 byte Jelly. ## Explained 7ε↔¬ 7ε # Abs difference of 7 with each item in the input ↔ # Remove items in that list that are also in the input ¬ # Logical negation - empty list turns into 1, non-empty turns into 0  • Shouldn't the explanation of '↔' read 'keep' instead of 'remove'? Commented Mar 14, 2023 at 15:11 # Jelly, 4 bytes 7_ḟƑ  Try it online! Relatively trivial golf of Erik's solution. 7_ For each face, subtract it from 7. Ƒ Is the list of results unchanged by ḟ filtering out elements of the original input?  Needless to say, a simple 7_f would win if inverted output were permitted. # ThunnoD, $$\ 5 \log_{256}(96) \approx \$$ 4.12 bytes 7_cS!  #### Explanation 7_cS! # Implicit input 7_ # Subtract each from 7 c # Is each in the input? S! # All are false? # Implicit output  # Nibbles, 6 bytes -~,&.$- 7\$


Attempt This Online!

Disgusting. Surely there is a better way to do this.

• Well, still disgusting, but at least half a byte shorter... Commented Mar 18, 2023 at 19:21

## Alice, 18 bytes

/..y1nr@
\iReA6o/


Try it online!

Prints Jabberwocky for valid inputs and nothing otherwise.

### Explanation

Unfolding the zigzag control flow, the program is really just:

i.e16r.RyAno

i.  Read all input and duplicate it.
e16 Push "16".
r   Range expansion to get "123456".
.R  Duplicate and reverse.
y   Transliterate, replaces each face with its opposite.
A   Intersection with input.
n   Logical NOT, turns empty strings into "Jabberwocky"
and everything else into an empty string.


# Pyth, 5 bytes

-7sM*


Test suite.

isaacg saved a byte!

## Retina, 20 bytes

T_654d
M(.).*\1
0


Try it online!

An alternative to Neil's approach.

### Explanation

T_654d


Turn 6,5, 4 into 1, 2, 3, respectively.

M(.).*\1


Try to find repeated characters and count the number of matches.

0


Make sure the result was zero (effectively a logical negation).

# Ruby, 36 31 24 23 bytes

->l{l-l.map{|x|7-x}==l}


Try it online!

It was so simple, I was looking for the solution to the wrong problem all the time.

# Factor + sets.extras, 24 bytes

[ 7 over n-v disjoint? ]


Try it online!

          ! { 2 1 3 }
7         ! { 2 1 3 } 7
over      ! { 2 1 3 } 7 { 2 1 3 }
n-v       ! { 2 1 3 } { 5 6 4 }
disjoint? ! t    (i.e. is the intersection empty?)


# Japt-x!, 5 bytes

fUma7


-1 byte thanks to Shaggy

This is basically a port of Lyxal's Vyxal answer.

fUma7  x!
f          # elements in both the input and
Um        #   the input, with each num mapped to
a7      #     its absolute difference with 7
x!  # flags: x = sum, ! = logical not

• Nicely done :) You can reverse it for 5 bytes: fUma7. Commented Mar 14, 2023 at 15:27

# Japt-!, 5 bytes

ï+ ø7


Try it

• Wow took me until today to realize that builtin meant cartesian product, very confusing description LOL. I thought it was [1, 2, 3] [4, 5, 6] -> [[1, 4], [2, 5], [3, 6]] Commented Mar 17, 2023 at 23:10

# C (GCC), 77 bytes

i,j;r;f(v,l)int*v;{for(i=r=-1;++i<l;)for(j=0;j<l;)r*=v[i]+v[j++]-7;return r;}


Try It Online!

Explanation:

i,j;r;
f(v,l)int*v;
{
// i and r are both initialized to -1. i is incremented by 1 before the
// loop, making its value equal 0, and for each iteration of the loop,
// until it's out of bounds of v.
for(i=r=-1;++i<l;)
// j also loops through the vector
for(j=0;j<l;)
// If v[i]+v[j] == 7, set r to 0, otherwise multiply it by
// something. If i == j, the sum will never equal 7 since a whole
// number multiplied by 2 is never odd. Otherwise, the numbers
// will equal 7 if they're on opposite sides of the die.
r*=v[i]+v[j++]-7;
return r;
}
`
• 65 bytes Commented Mar 18, 2023 at 8:11