[Question]
  [
While I was writing numbers I noticed after a while that my keyboard had the `Shift` key pressed and blocked and all I wrote was `$%&`-like characters. And even worse, I had been switching between the English and Spanish keyboard layouts so I don't know which one I used for each number.
### Challenge
Given a string containing symbol characters, try to guess which number I wrote. My keyboard produces the following characters for the numbers when the `Shift` is pressed:
```
1234567890
----------
!"·$%&/()=  Spanish layout
!@#$%^&*()  English layout
```
* The input will be a non-null, non-empty string composed of the symbols above.
* The output will be a single number if the keyboard layout can be inferred from the string (i.e. if the string contains a `@` an English layout was used, and if the string contains a `"` a Spanish layout was used) or if the number is the same for both layouts (i.e. the input is `!$` which translates as `14` for both layouts); otherwise the output will be the two possible numbers for both layouts if it cannot be inferred and the resulting numbers are different.
* The input string will always be written in a single layout. So you don't need to expect `"@` as input.
### Examples
```
Input  -->  Output
------------------
/()         789        (Spanish layout detected by the use of /)
$%&         456,457    (Layout cannot be inferred)
!@#         123        (English layout detected by the use of @ and #)
()&!        8961,9071  (Layout cannot be inferred)
((·))       88399      (Spanish layout detected by the use of ·)
!$          14         (Layout cannot be inferred but the result is the same for both)
!!$$%%      114455     (Layout cannot be inferred but the result is the same for both)
==$"        0042/42    (Spanish layout, if a number starts with 0 you can choose to
                       omit them in the result or not)
Single character translations:
------------------------------
!   1    
"   2
·   3
$   4
%   5
&   6,7
/   7
(   8,9
)   9,0
=   0
@   2
#   3
^   6
*   8
```
This is [code-golf](/questions/tagged/code-golf "show questions tagged 'code-golf'"), so may the shortest code for each language win!
  
[Answer]
# [Jelly](https://github.com/DennisMitchell/jelly), ~~32~~ 31 bytes
```
O“=!"Ṣ$%&/()“)!@#$%^&*(‘iⱮ€PƇ’Q
```
[Try it online!](https://tio.run/##rZDPSsNAEMbvfYrJvzaRQJM2aZtDoRdvgopHUUiajYkku5JskN6Kl76CgifPRfAkXhV8D/MicZLWmoJSBOewMLs7v@/75pLE8awsD4v5/VgQP14eZKXdVTVsNWEiycp5e08t5rdR8fRY3CyP3hfF/O64fFtgU5anLRH/ilCXXh3ScOTAutSTK5dGWQixO2M5B59wMuXEB28GPCSQZwRYAF2tJaLoFsWyB7plD2vKwWp66lLKOHgEIhqQNCU@zqHFrTmz19@o79OLeLf6BFzqg4QsVWsLYoM1cgam7hhDc4cHVX191lZLWA@O@o7zpxUgALPI6yhfWSzYZPlVHzy8rkgpyfKYQ5TVXeYmBAKWgsd4WLEFWVYU8ZttWpZt/wu7Mx7LYqfh2zCsXtfq/RBfhygAF2ieeCSFjLspz@A64iEYgO@VBZiGjOFSOGudwXZJzYYlUe0tQbdNj2gLU2jwCQ "Jelly – Try It Online")
* -1 bytes thanks to Erik the Outgolfer
---
```
O“!"Ṣ$%&/()=“!@#$%^&*()‘iⱮ€PƇ%⁵Q
O                                  ord of each character in the input
 “!"Ṣ$%&/()=“!@#$%^&*()‘           Constant that yields the list:
                                      [[33, 34, 183, 36, 37, 38, 47, 40, 41, 61],
                                       [33, 64, 35, 36, 37, 94, 38, 42, 40, 41]
                          €        For each list of numbers:
                         Ɱ           For each ord of the characters in the input:
                        i              Find the index of the ord of the character
                                       in the list of numbers.
                                       If the number is not found, `i` returns zero
                                       which means it's a character from only one
                                       keyboard.
                                   There are now two lists of numbers 1-10.
                            Ƈ      Keep the list(s) that: 
                           P         have nonzero product.
                             %⁵    Modulo 10. This maps 10->0.
                               Q   Unique elements. This removes duplicates if the two numbers are the same.
```
[Answer]
# [Python 3](https://docs.python.org/3/), 76 bytes
```
lambda s:{(*map(k.find,s),)for k in['=!"·$%&/()',')!@#$%^&*(']if{*s}<={*k}}
```
[Try it online!](https://tio.run/##rVK7bsIwFN39FTchEBtFECABghqJpVu3jkAlhziNRbCj2KhCiO9i58eoQwld@lClerq@x@dxbZd7nUsxumTx8lLQbZJSULMD7m5piTe9jIvUU8QjmaxgA1ws3Niyzyen3elj4nouseYtp/3S6WJ3xbNDVx0f4kN3czxeVGzb9hKZY9CsyTRqSvxcUsFVDgXdy52GlGm21iyFZA86Z7BTDGQGfYKM1V0gCMdeEE6uAk8fxDUVQmpImAmXsapiKUEm050yGI7uno/itfjdcw5UpNAiCJOO1XCn0XjgRf5k8LMzxucTaQaeTkdR9KdxDRlZDnyGD@7l966QmHYtUjG1KzRwdd0pumVQP1sidW5kLcdpt2@ygyAIw3@RjWPHbiL6fjDsB8Mv5vWAZ0BB7LYJq0BpWmkFb1zn4IPBa3dY51KaW9DSfBuEaoeCizoOqJ4qC66xuxQumSEwvRLiK3xDyMJfmX5ZcaFxhg1OCLq8Aw "Python 3 – Try It Online")
[Answer]
# [Perl 6](https://github.com/nxadm/rakudo-pkg), 62 bytes
```
{set grep {!/\D/},TR'=!"·$%&/()'0..9',TR')!@\x23$%^&*('0..9'}
```
[Try it online!](https://tio.run/##JcvBCoJAEAbgV/lHZ9cZCTcKgqANDz1BdBSjg3YpEu2QiM/l3RfbjK4ffE3VPnbh2cPW8GHoqjfubdVgIFec3Li6nBNP0TyxsU40WWfZPvmhUl58Nls2pU3lz2Pobj1q4auifrU4LAHLA@UxRC1BZJ5UQQwiZmPgPUcgRJgnMAwsHAQKjxwxSqTH8AU "Perl 6 – Try It Online")
Returns a Set. (Could be made two or three bytes shorter if [there wasn't a bug](https://github.com/rakudo/rakudo/issues/2118) in Rakudo's handling of # in search lists.)
[Answer]
# [Java (JDK)](http://jdk.java.net/), 173 bytes
**Golfed**
```
c->{String s="",e=s;var m="21#3457#908###6##12#456389###0#7".split("");for(int l:c){e+=m[l=l%16];s+=m[l+16];}return s.equals(e)|s.contains("#")?e:e.contains("#")?s:s+","+e;}
```
[Try it online!](https://tio.run/##lZLLTsMwEEXX5CscO0G20oa@X5F5iDXddFm6MK5bUpyk2E6lKuS72PNjwW2zQCAWmZVn5tzR3JF37MDau/Vbtc9fZMwBl0xr8MTitHCuHGBDG2ZsI06NUBvGBZgX5/opatHCqDjdAo75K1PLFeAkOiOl83PCHKSAAqfi7duiVmgKYUtQHR2YAgmFvS7qD4ZjNO1MEEIjhLo9NBiO@pOpTTtoDEO9l7HBEJJokylslwJyxkkhAposJZV@d7SK9DkJTs9SCZOrFOhQvOdMaizIhw55lhrrUGOIILkTM/Gromc6gC0YiKisoouH2mlt5ZDFa5BYAb4YsZ6Z2mpib7Y4aiOSMMtNuLctI1OchhzDG0xgaLJHe6EHpdgRE2Kv9C/u@ddNcPceNcExuXYb8fjrkzTa3/Ua0a7n@X4TBaXeM/wrAKD@eGX1DQ "Java (JDK) – Try It Online")
---
**Ungolfed**
```
c->{                                                      // Lamdba taking char array as input
    String s="",e=s;                                      // Initialise Spanish and English strings
    var m="21#3457#908###6##12#456389###0#7".split("");   // Create magic hashing lookup array (see below)
    for(int l:c){                                         // Loops through all chars in input
        e+=m[l=l%16];                                     // Get english number from array and append
        s+=m[l+16];                                       // Get Spanish number from array and append
    }
    return s.equals(e)|s.contains("#")?e:                 // If equal or Spanish is invalid return english
        e.contains("#")?s:                                // If English is invalid return Spanish
        s+","+e;                                          // If both are valid but not equal, return both
}
```
---
**The Magic Hashing Lookup Array**
After some experimenting with values I realised that each of the ASCII values of the characters `!"·$%&/()=@#^*` modulo 16 returns a unique number. The *'magic hashing lookup array'* stores the English numbers associated with each character at this unique index, and each of the Spanish numbers at this index offset by 16, making fetching the required number from the array trivial for each language. A hash is stored for values that are invalid for either language.
[Answer]
# Japt, 38 bytes
Outputs an array of strings with the Spanish layout first.
```
"=!\"·$%&/())!@#$%^&*("òA £ËXbD
kø'- â
```
[Try it](https://ethproductions.github.io/japt/?v=1.4.6&code=Ij0hXCK3JCUmLygpKSFAIyQlXiYqKCLyQSCjy1hiRApr+CctIOI=&input=Jy8oKScKLVE=)
[Answer]
# [Jelly](https://github.com/DennisMitchell/jelly), 38 bytes
```
183Ọ“=!"“$%&/()”j,“)!@#$%^&*(”iⱮ€⁸ẠƇ’Q
```
[Try it online!](https://tio.run/##y0rNyan8/9/Qwvjh7p5HDXNsFZWApIqqmr6G5qOGuVk6QJ6mooOyimqcmpYGUCTz0cZ1j5rWPGrc8XDXgmPtjxpmBv7//19D49B2TU0A "Jelly – Try It Online")
[Answer]
# [Retina 0.8.2](https://github.com/m-ender/retina/wiki/The-Language/a950ad7d925ec9316e3e2fb2cf5d49fd15d23e3d), 60 bytes
```
.+
$&¶$&
T`=!"·$%&/()`d`^.+
T`)!@#$%^&*(`d`.+$
D`
Gm`^\d+$
```
[Try it online!](https://tio.run/##DYs9DsIwDIX3dwuXZ8shUjlBJAakXqAjioxUBgYYEGdr91wsZP1@vs/f6/Po6kv0OYPWdhrWKDK1g2oXT7FFHWqNJNcTtdrZB5ozcQss76j3LbMTbe@jxpgwQngygXs7UoIQIqQqSuH0Bw "Retina 0.8.2 – Try It Online") Link includes test cases. Explanation:
```
.+
$&¶$&
```
Duplicate the input.
```
T`=!"·$%&/()`d`^.+
T`)!@#$%^&*(`d`.+$
```
Try to translate each line according to a different keyboard layout.
```
D`
```
Deduplicate the result.
```
Gm`^\d+$
```
Only keep lines that only contain digits.
[Answer]
# JavaScript (ES6), 99 bytes
```
s=>(g=l=>a=s.replace(/./g,c=>l.indexOf(c)))('=!"·$%&/()',b=g(')!@#$%^&*('))>=0?a-b&&b>=0?[a,b]:a:b
```
[Try it online!](https://tio.run/##ZY7RaoMwFIbv9xS1jTEZqVEbqxaO2xv0AcYGSRqlI2ipZezNet8Xc8k6VtBz9cP3Hf7/U37JQZ@Pp8u66w9mbGAcoCYtWKglDPHZnKzUhvCYt0xDbeNjdzDf@4ZoSimJIFjerijEnNCIKWhJRIPXFQo/8LOLtIbkRa4VxsqnN8nU@07u1Kj7buitiW3fkoZE/pvShTvOF0VZPU24K3hwkW@ZyIup42ofTpptppxQHNwFx8tqm7IqKdKZRW5Xeh/jtXJTzcYE6K/nt0jMcIBQGHrF41SIPJ8qAGj5PyVJRMZFNv4A "JavaScript (Node.js) – Try It Online")
### How?
The helper function \$g\$ attempts to convert the input string using a given layout.
Invalid characters are replaced with \$-1\$, which results in either a valid but negative looking numeric string (if only the first character was missing), or an invalid numeric string. Either way, the test `x >= 0` is falsy.
[Answer]
# [05AB1E](https://github.com/Adriandmen/05AB1E/wiki/Commands), ~~42~~ 41 [bytes](https://github.com/Adriandmen/05AB1E/wiki/Codepage)
```
•Hhç₁d©u÷^Σ(“ðΣèõĆ
-•184в2äεIÇk}ʒ®å_}>T%Ù
```
Port of [*@dylnan*'s Jelly answer](https://codegolf.stackexchange.com/a/173950/52210).
[Try it online](https://tio.run/##AVAAr/9vc2FiaWX//@KAokhow6figoFkwql1w7dezqMo4oCcw7DOo8Oow7XEhgot4oCiMTg00LIyw6TOtUnDh2t9ypLCrsOlX30@VCXDmf//KCkmIQ) or [verify all test cases](https://tio.run/##AYEAfv9vc2FiaWX/fHZ5PyIg4oaSICI/eVX/4oCiSGjDp@KCgWTCqXXDt17OoyjigJzDsM6jw6jDtcSGCi3igKIxODTQsjLDpM61WMOHa33KksKuw6VffT5UJcOZ/yz/LygpCiQlJgohQCMKKCkmIQooKMK3KSkKISQKISEkJCUlCj09JCI).
**Explanation:**
```
•Hhç₁d©u÷^Σ(“ðΣèõĆ
-•184в           # Compressed list [33,34,183,36,37,38,47,40,41,61,33,64,35,36,37,94,38,42,40,41]
      2ä         # Split into two parts: [[33,34,183,36,37,38,47,40,41,61],[33,64,35,36,37,94,38,42,40,41]]
ε   }            # Map each inner list to:
 IÇ              #  Get the input, and convert each character to its unicode value
   k             #  Then get the index of each unicode value in the current map-list
                 #  (this results in -1 if the item doesn't exist)
     ʒ   }       # Filter the resulting list of indices by:
      ®å_        #  If the inner list does not contain any -1
          >      # Increase each index by 1 to make it from 0-indexed to 1-indexed
           T%    # Take modulo-10 to convert 10 to 0
             Ù   # Uniquify the result-lists (and output implicitly)
```
[See this 05AB1E tip of mine (section *How to compress integer lists?*)](https://codegolf.stackexchange.com/a/166851/52210) to understand why `•Hhç₁d©u÷^Σ(“ðΣèõĆ\n-•184в` is `[33,34,183,36,37,38,47,40,41,61,33,64,35,36,37,94,38,42,40,41]`). This (together with the `2ä`) is 1 byte shorter than taking the unicode values of the string: `'""!ÿ·$%&/()=""!@#$%^&*()"‚Ç`.
[Answer]
# [Ruby](https://www.ruby-lang.org/), 68 bytes
```
->s{%w[=!"·$%&/() )!@#$%^&*(].map{|a|s.tr a,'0-9'}.grep_v(/\D/)|[]}
```
[Try it online!](https://tio.run/##Jc1RCoIwHIDx9/8pNtt0C916DVz00CGEZWGgIlgMZ2U4z@W7F7NRB/h@X/e8fdZKrcnBjvStFQ6WmdBQMo44Pm4IvYRblot7YUZXOCv6DhVxtEv20STqrjTXF5Pnk@RO59PaNo/SqjTNhDVt0yMiwUPgPfAWMB5iYGyZOQdMAGNCKAWlSAAZ/Nr/Z3AG6SGu9JB79As "Ruby – Try It Online")
[Answer]
# [Clean](https://github.com/Ourous/curated-clean-linux), 116 bytes
```
import StdEnv,Text
$s=removeDup[foldl(<+)""d\\r<-["=!\"·$%&/()",")!@#$%^&*("],d<-[[indexOf{c}r\\c<-s]]|all((<) -1)d]
```
[Try it online!](https://tio.run/##JY1NC4IwAEDv/Yq1TLdSojp0UehghyAoqJtbMLYZwj5kziiqv94SOj54j8eVZCZoK3olgWaNCY1urfPg7MXO3NOLfPhR1BVOanuXZd9WtVVCoXyOIRSEuDyrYDEmkKw3q2gaLxCGKcTj7SSaXuMZgjQVg1I1RsjHsX7xjyOE51lH6ZsphVCOQbbEgoazZ8O2ABGokiFPaPjyWrFbF7L9IZRPw3TD/3BSzNfW6R8 "Clean – Try It Online")
Takes input and is encoded in CP437. TIO only supports UTF-8, so an escape is used in the demo code to get the literal byte value 250 corresponding to the centre dot (counted as one byte).
[Answer]
# [APL (Dyalog)](https://www.dyalog.com/), 40 [bytes](https://codegolf.meta.stackexchange.com/a/9429/43319 "When can APL characters be counted as 1 byte each?")
Anonymous tacit prefix function. Though unused, `·` [is in the Dyalog single byte character set](https://tio.run/##SyzI0U2pTMzJT/8PBOqHtqs/6uh61DfVMQwA "APL (Dyalog Unicode) – Try It Online"). Assumes 0-based indexing (`⎕IO←0`) which is default on many systems.
```
{∪⍵/⍨~10∊¨⍵}'=!"·$%&/()' ')!@#$%^&*('⍳¨⊂
```
[Try it online!](https://tio.run/##SyzI0U2pTMzJT///qG@qp/@jtgkG/6sfdax61LtV/1HvijpDg0cdXYdWALm16raKSoe2q6iq6Wtoqiuoayo6KKuoxqlpaag/6t0MVNLV9D8NqP9Rbx/EqK7mQ@uNH7VNBPKCg5yBZIiHZ/D/NAV1kH4uIA00CkwDDQLTGppqihCGxqHtmhA1iioQSlFFRVUVzLS1VVFSBwA "APL (Dyalog Unicode) – Try It Online")
`⊂` the entire argument
`'=!"·$%&/()' ')!@#$%^&*('⍳¨` indices of the characters in each of these strings
`{∪⍵/⍨~10∊¨⍵}` apply the following lambda (`⍵` is the argument):
`10∊¨⍵` for each list of digits, whether 10 (indicating "not found") is a member thereof
 `~` local negation (i.e. only those where all digits are found)
 `⍵/⍨` filter the argument by that
 `∪` find the unique elements of that
[Answer]
# [Dart](https://www.dartlang.org/), 125 bytes
```
f(s)=>['=!"·\$%&/()',')!@#\$%^&*('].map((b)=>s.split('').map((e)=>b.indexOf(e)).join()).where((e)=>!e.contains('-')).toSet();
```
Ungolfed :
```
f(s){
  ['=!"·\$%&/()',')!@#\$%^&*(']
    .map(
      (b)=>s.split('').map((e)=>b.indexOf(e))
      .join()
    ).where(
      (e)=>!e.contains('-')
    ).toSet();
}
```
* Creates an array with the two specified key values, from 0 to 9
* For each of them, convert the input string to the corresponding number by using the characters' indexes
* Join the resulting array to create a number
* Remove any number having a '-' (Dart returns -1 when indexOf can't find a char)
* Return as a Set to remove duplicates
[Try it on Dartpad!](https://dartpad.dartlang.org/4a2cde45e47d38c8fbaa2358053e726c)
[Answer]
# T-SQL, 143 bytes
```
SELECT DISTINCT*FROM(SELECT TRY_CAST(TRANSLATE(v,m,'1234567890')as INT)a
FROM i,(VALUES('!"·$%&/()='),('!@#$%^&*()'))t(m))b
WHERE a IS NOT NULL
```
Input is taken via pre-existing table **i** with varchar field **v**, [per our IO standards](https://codegolf.meta.stackexchange.com/questions/2447/default-for-code-golf-input-output-methods/5341#5341).
Joins the input table with the two different character strings, then uses the [new SQL 2017 function `TRANSLATE`](https://docs.microsoft.com/en-us/sql/t-sql/functions/translate-transact-sql) to swap out individual characters, and `TRY_CAST` to see if we end up with a number. If not, `TRY_CAST` returns `NULL`.
The final outer `SELECT DISTINCT` combines identical results and filters out the `NULLS`.
]