[Question]
  [
An old test for programmers, taken from [here](https://www.facebook.com/notes/dario-dariol/il-pifferaio-magico/10157974434244334/) (Note: in italian).
Along a road (denoted by '`_`'), there is a Magical Piper (denoted by '`P`') and several mice (represented by the two characters 'o' and '`~`', that denote respectively the head and the tail of the small rodents).
Write a program that prints how many mice are going towards the Piper and how many mice are going away from him. 
The input is a string, the output are two numbers, the first the number of mice that go towards the Piper, the second the number of mice that go away from the Piper. 
The input can be also a list or vector of characters, and the output 
a vector or list of two numbers. You can assume that the input is always correct.
Both programs as well as functions are allowed.
Examples:
input: `__o~P_o~~o`
output: `1 2`
input: `__P~oo~o~_o~~o__`
output: `3 2`
input: `~oPo~` 
output: `2 0`
input: `o~P~o`
output: `0 2`
---
This is code golf, so the shortest program in any language wins.
**Note:** In the question, I've removed the requirement of an error message, given the majority prefer it this way. Sorry for people that already coded the error test!
  
[Answer]
# [Ruby](https://www.ruby-lang.org/), ~~128 .. 51~~ 49 bytes
```
->w{%w(o ~).map{|c|w.scan(/_*._*(.)/).count [c]}}
```
[Try it online!](https://tio.run/##KypNqvyfZvtf1668WrVcI1@hTlMvN7Gguia5plyvODkxT0M/XksvXktDT1NfUy85vzSvRCE6Oba29n@BQlq0Unx8fl0AENflK8VyQUUC6vLz6/LrwKLx8Uqx/wE "Ruby ‚Äì Try It Online")
No error checking.
### How:
* Ignore all underscores
* All mice going towards the piper have the head in an odd-numbered (0-based) position.
* All mice heading away from the piper have the tail in an odd-numbered position.
* Take every 2nd character (skipping underscores), count heads and tails.
# [Ruby](https://www.ruby-lang.org/) (with error checking), ~~109 99~~ 97 bytes
```
->w{w.chars+w.scan(/[o~]./)-%w(o ~ _ ~o o~)==[?P]?%w(o ~).map{|c|w.scan(/_*._*(.)/).count [c]}:q}
```
[Try it online!](https://tio.run/##lY7NCoJAFIX3PcVFCJzCcS@Y25azH4aLDUqbvDYqg6j31U3KQNpUi7P5zg/HdZd@LtM5OvnBS3vNXXP0srF5Fcaa2MhYRHsfEjAgMAGxSFOdKZO9qJC3vB5GO75LeJB4CKWIhbTUVS1oa6bkPs01lDpAJFaLmAKzW4liIiZ@UsSFt66H1Tt/eOCKxnYF1F3bQFI4R24b306pH@L41zp@PzM/AA "Ruby ‚Äì Try It Online")
Thanks Value Ink for -2 bytes on both.
[Answer]
# [05AB1E](https://github.com/Adriandmen/05AB1E/wiki/Commands), ~~13~~ ~~11~~ 10 [bytes](https://github.com/Adriandmen/05AB1E/wiki/Codepage)
```
'_KƒÅ√à√èaTS¬¢
```
Port of [*@GB*'s Ruby answer](https://codegolf.stackexchange.com/a/199033/52210), so make sure to upvote him!!  
-1 byte thanks to *@Grimmy* by taking the input as character-list.
[Try it online](https://tio.run/##yy9OTMpM/f9fPd77SOPhjsP9iSHBhxb9/x@tFK@kA8YBQFwHxPlQXIdExyOxYeIQfbEA) or [verify all test cases](https://tio.run/##yy9OTMpM/V9TVmmvpPCobZKCkn1l8H/1eO8jjYc7DvcnhgQfWvRf5398fH5dABDX5XPFxwfU5efX5deBufHxXHX5Afl1XED5unwA).
**Explanation:**
```
'_K        '# Remove all "_" from the (implicit) input-list
   ƒÅ        # Push a list in the range [1, length] (without popping the list)
    √à       # Check for each whether it's even
     √è      # Only keep the characters at these even 1-based indices
      a     # Check for each remaining character whether it's a letter or not
            # (1 if 'o'; 0 if '~')
       TS   # Push 10 as digit-list: [1,0]
         ¬¢  # And count each in the list of 0s and 1s
            # (after which this pair of counts is output implicitly as result)
```
[Answer]
# [JavaScript (Node.js)](https://nodejs.org), ~~80 66 65 58~~ 57 bytes
Returns `[towards, away]`.
```
s=>Buffer(s).map(c=>c%3?i^=~c:a[c&1]+=++i&1,a=[i=0,0])&&a
```
[Try it online!](https://tio.run/##bYxBDoIwEEX33sPSpkgg7kwGE0/QPcFmUltTAwyh6nKuXglbWfzN@y/vhV9Mbonz@zTRw@cAOUF7@4TgF5lUNeIsHbTueL7GO7C7YOdE02vQOoqmROgi1GXdKyEwO5oSDb4a6CmDLKwlNuuYCqUOf6dhIibeBGt3FCZDvMPX6pbMPw "JavaScript (Node.js) ‚Äì Try It Online")
### How?
An efficient way to determine whether the character is a mouse body part is to take the ASCII code modulo \$3\$.
Quite conveniently, we can also distinguish between `P` and `_` or between `o` and `~` by simply testing the parity of the corresponding ASCII codes.
```
 character  | 'P' | '_' | 'o' | '~'
------------+-----+-----+-----+-----
 ASCII code |  80 |  95 | 111 | 126
 modulo 3   |   2 |   2 |   0 |   0
 modulo 2   |   0 |   1 |   1 |   0
```
### Commented
```
s =>                       // s = input string
  Buffer(s)                // turn s into a buffer
  .map(c =>                // for each ASCII code c:
    c % 3 ?                //   if c modulo 3 is not equal to 0:
      i ^= ~c              //     invert the least significant bit of i if c is even
                           //     (must be 80, for 'P')
    :                      //   else:
      a[c & 1] += ++i & 1, //     update a[0] if c is even (126 -> '~')
                           //     or a[1] if c is odd (111 -> 'o')
                           //     increment i and add its parity
    a = [i = 0, 0]         //   start with a = [0, 0] and i = 0
  ) && a                   // end of map(); return a[]
```
---
# [JavaScript (Node.js)](https://nodejs.org), ~~112~~ 102 bytes
A version with error checking, as per the original rules of the challenge.
```
s=>Buffer(s).some(c=>n?n-=c:c-111&&c-126?c-95?c-80|p++:0:!++a[n=c^17,p^c&1],a=[n=0,p=0])|p-1?'error':a
```
[Try it online!](https://tio.run/##dczLCsIwEAXQvX/hpk1pUxrBVyAt@AXdSxtCTESpmZCoq5Jfr/GxUxczA3Mu9yzuwkt3slds4KAmzSbP6t1Na@WQz0oPF4Ukq01jMJNUYkJIksSzWDUSb5dxbarR5jmt6DzPxd4w2ZN1YXuZkK4QLD6qwrKqy0aLSZMq58ClVEwSjIdBlQMckUYp5xDaOAHSLJt9YRsAAoRXgPOfkY/@sXd3@1t5LH3S9AA "JavaScript (Node.js) ‚Äì Try It Online")
[Answer]
# [Python 2](https://docs.python.org/2/), 47 bytes
Port of [G B's Ruby answer](https://codegolf.stackexchange.com/a/199033/64121).
```
lambda s:map(s.replace('_','')[::2].count,'~o')
```
[Try it online!](https://tio.run/##HcgxDoQgEEDR3lNMN5AQC0sS72CvZoKuRBNlCGBhM1dn3S1@8V98ys6hq76f6umu5eMg28tFldu0xdOtm0JCg6hHa7u5XfkOxaAw6uo5QYYjABKxDG8vm98NwiwsfyFC2wDEdIQCXmVdvw "Python 2 ‚Äì Try It Online")
[Answer]
# [Python 2](https://docs.python.org/2/), ~~252~~ \$\cdots\$ ~~71~~ 72 bytes
Saved 29 bytes thanks to [JoKing](https://codegolf.stackexchange.com/users/76162/jo-king)!!!  
Saved 2 bytes thanks to [ovs](https://codegolf.stackexchange.com/users/64121/ovs)!!!  
Saved a byte thanks to [ReinstateMonica](https://codegolf.stackexchange.com/users/85755/reinstate-monica)!!!  
Saved 21 bytes thanks to [KevinCruijssen](https://codegolf.stackexchange.com/users/52210/kevin-cruijssen)!!!  
Added a byte to fix a bug kindly pointed out by [JoKing](https://codegolf.stackexchange.com/users/76162/jo-king).
```
def f(s):
 r=[0,0];i=0
 for c in s:
	if'_'!=c:r[c>'o']+=i;i^=1
 return r
```
[Try it online!](https://tio.run/##HY6xDsMgDETn8hVuFhI1A@1IRL@BPUoZaFBZcARk6OJfp6aWrJNP93Q@vvWD6dHaew8QxjJpAdmsalbbEo0SEDCDh5igaHGJQTp5NV7n1T8lyu1m4hJf5s7QXs@cILcOlA4MziFZXsJh5sMSIiH9DefYIrRIrJziCBfzHDmmOvZHpvYD "Python 2 ‚Äì Try It Online")
Inputs a string and outputs a list.
[Answer]
# [J](http://jsoftware.com/), ~~27~~ 19 bytes
```
[:+/_2=&'~'\'_'-.~]
```
[Try it online!](https://tio.run/##y/qvpKeepmBrpaCuoKNgoGAFxLp6Cs5BPm7/o6209eONbNXU69Rj1OPVdfXqYv9rcnGlJmfkKxgqGCnoWimkKajHx@fXBQBxXb46RMoYSSqgLj@/Lr8OLB0fD1VgBLIDrKAuPyC/DipqANcGNA9o2H8A "J ‚Äì Try It Online")
This took inspiration from both [Kevin's answer](https://codegolf.stackexchange.com/a/199044/15469) and [GB's answer](https://codegolf.stackexchange.com/a/199033/15469).
## how
We'll work through an example: `__o~P_o~~o`
* `'_'-.~]` Remove the underscores:
```
o~Po~~o 
```
* `_2=&'~'\` For every two characters, create a boolean mask where 1 indicates that the character in that position is `~`:
```
0 1  o~
0 0  Po
1 1  ~~
0 0  o 
```
* `[:+/` Sum the colums:
```
1 2
```
[Answer]
# [Retina](https://github.com/m-ender/retina/wiki/The-Language), 31 bytes
```
+`o~(?!o)
1
T`1~`~1`.*P
*\C`1
~
```
[Try it online!](https://tio.run/##K0otycxLNPz/Xzshv07DXjFfk8uQKyTBsC6hzjBBTyuASyvGOcGQq@7///j4gLr8/Lr8uvj8urr8@HgA "Retina ‚Äì Try It Online")
### Explanation
```
+`o~(?!o)
1
```
Recursively replace all mice walking to the left with a `1`. Mice walking to right stay as they are.
```
T`1~`~1`.*P
```
Swap `1` and `~` at all positions up to the `P`.
```
*\C`1
```
Every `1` stands for a mouse walking towards the Magical Piper. Count the `1`'s and output the result without changing the current string.
```
~
```
Count `~`'s (implicit output). every `~` stands for a mouse walking away from the Magical Piper.
---
# [Retina](https://github.com/m-ender/retina/wiki/The-Language), ~~23~~ 18 bytes
port of [G B's Ruby answer](https://codegolf.stackexchange.com/a/199033/64121). 5 bytes shorter thanks to [Neil](https://codegolf.stackexchange.com/users/17602/neil).
```
_
(.).
$1
*\C`~
o
```
[Try it online!](https://tio.run/##K0otycxLNPz/P56LS0NPU49LxZBLK8Y5oY4rHygWH1CXn1@XXxefX1eXHx8PAA "Retina ‚Äì Try It Online")
[Answer]
# [JavaScript (Node.js)](https://nodejs.org/en/), ~~57~~ 54 bytes
```
s=>Buffer(s).map(c=>a[~c&1]+=c%19&&i++%2,a=[i=0,0])&&a
```
Alternative JavaScript answer for [the existing JavaScript answer](https://codegolf.stackexchange.com/a/199034/52210) ~~(of equal byte-count at time of writing)~~, which I figured was worth posting as separated answer. Loosely based on [my Java 8 answer](https://codegolf.stackexchange.com/a/199049/52210) and inspired by [*@GB*'s Ruby answer](https://codegolf.stackexchange.com/a/199033/52210).
-3 bytes thanks to *@Arnauld*.
[Try it online.](https://tio.run/##bYwxDoMwEAT7/ANjywRBuhRHkRe4R8g6OXbkiHAIB8r7uoNoQ7HN7GjeuGFyS5y/14mePgfICbrHGoJfZFL1B2fpoMOenWgHDa5o70JErYtbhdBHaKpmUEJgdjQlGn090ksGWVpLbPYxlUpd/k7DREx8CNaeKEyG@ITv1SOZfw)
**Explanation:**
```
s=>                 // Method with string as parameter and integer-array as result
  Buffer(s).map(c=> //  Loop over the characters in the String as codepoint integers:
    a[~c&1]+=       //   Increase the count at index (c+1)%2 by:
      c%19&&        //    If c modulo-19 is NOT 0:
            i++%2,  //     Add i%2 to the count, and increase i by 1 afterwards
    a=[i=0,0]       //  Start the counts at [0,0] and i at 0
  )&&a              //  After the loop, return this resulting pair of counts
```
The codepoints of the four used characters are `'P'=80, '_'=95, 'o'=111, '~'=126`, which I'm using to my advantage:
* The `~c&1` will result in index `0` for the character `'o'` and index `1` for character `'~'`. (It will also result in index `1` for character `'P'` and index `0` for character `'_'`, but this won't cause any issues.)
* The modulo-19 is to ignore `'_'` characters. Using the modulo-19 on the four codepoints results in `4,0,16,12` for `P_o~` respectively, for which the `'_'` is falsey and the other three are truthy.
The `i++%2` will only add `1` to the count for odd-indexed characters. All even-indexed characters won't affect the counts. Since the `'P'` is guaranteed to be at an even-indexed position (when ignoring the `'_'` with `c%19&&`), the count for character `'P'` will always increase by `0`, and thus stay the same.
[Answer]
# JavaScript (ES6)
Port of [G B's Ruby answer](https://codegolf.stackexchange.com/a/199033/64121).
```
a=>a.filter(v=>v!='_').map((v,i)=>i%2||v=='P'?0:a[+(v=='o')]++,a=[0,0])&&a
```
[Answer]
# [C (gcc)](https://gcc.gnu.org/), ~~¬†87¬†~~ 85 bytes
*Saved 2 bytes thanks to [@xibu](https://codegolf.stackexchange.com/users/90181/xibu)*
Prints the results as `towards away`.
```
a,b,p;f(char*s){for(a=b=p=0;*s;s++)*s%3?p|=~*s:p+*s++&1?b++:a++;printf("%d %d",a,b);}
```
[Try it online!](https://tio.run/##bYxNCoMwFIT3niIELPlRaOnOELyCNwgxohVaXzC2XVjf0ZsGoTsXA8PMx@fKwbkYbdEWXvXM3ewsAl97mJnVrfb6rERQQUouQn6t/UejCJWXIk2nS91KWVkplZ/HaekZzTuSd7RIOq62@IKxIw87ToyTNSMkAcYANikIlCvin0tgNLX/2SAAAu6AMQcIQgN4sCfrrsy2@HX93Q4hlu8f "C (gcc) ‚Äì Try It Online")
### Commented
```
a,                       // a = 'towards' counter
b,                       // b = 'away' counter
p;                       // p = piper flag
f(char *s) {             // f is function taking a pointer to a string s
  for(                   // main loop:
    a = b = p = 0;       //   start with a = b = p = 0
    *s;                  //   go on while the end of the string is not reached
    s++                  //   advance the pointer after each iteration
  )                      //
    *s % 3 ?             //   if the current character is not a mouse body part:
      p |= ~*s           //     set the piper flag if the ASCII code is even (80 -> 'P')
    :                    //   else:
      p + *s++ & 1 ?     //     test the parity of (p + current ASCII code) and advance
                         //     the string pointer to skip the next body part
                         //     if odd:
        b++              //       increment b
      :                  //     else:
        a++;             //       increment a
  printf("%d %d", a, b); // print the results
}                        //
```
---
# [C (gcc)](https://gcc.gnu.org/), ~~¬†72¬†~~ 70 bytes
*Saved 2 bytes thanks to [@mypronounismonicareinstate](https://codegolf.stackexchange.com/users/36445/my-pronoun-is-monicareinstate)*
This version saves the results in an array passed as a 2nd argument. I don't know for sure if it's acceptable.
```
p;f(char*s,int*r){for(*r=r[1]=p=0;*s;s++)*s%3?p|=~*s&1:r[p^*s++&1]++;}
```
[Try it online!](https://tio.run/##lU7RCoJAEHz3K45A8U4FrbcO6Rd8t0vkRBPKPfaiHsz79K6zKHq0hV3YnZmdkUknpbWKt6E81sh03A8XhnRsAUOGOZaZyFWecqa5jiLKtL/ZqXtumA6yLZbqwNw5yEQU8cleoW/Iue6HkJLRI8T9IliuBffc0oarqgJTuDawism7kHKi0BEd7DfEb/aDw7BMxTwzQflHWhgAA@Ylr6qZtFBqoADzNfzL1cX9ybpUOtmHbE91p21yewI "C (gcc) ‚Äì Try It Online")
[Answer]
# [05AB1E](https://github.com/Adriandmen/05AB1E), 17 bytes
```
'P¬°`RJ'_K2√¥‚Äû~o√Ç‚Äö¬¢
```
[Try it online!](https://tio.run/##ATMAzP9vc2FiaWX//ydQwqFgUkonX0syw7TigJ5@b8OC4oCawqL//19fUH5vb35vfl9vfn5vX18 "05AB1E ‚Äì Try It Online")
[Answer]
# [MATL](https://github.com/lmendo/MATL), 25 bytes
```
80&Yb"@g'o~'&mXz2eq!Xs]P+
```
[Try it online!](https://tio.run/##y00syfn/38JALTJJySFdPb9OXS03osootVAxojg2QPv/f/X4@IC6/Py6/Lr4/Lq6/Ph4dQA "MATL ‚Äì Try It Online")
[Answer]
# [Pyth](https://github.com/isaacg1/pyth), 14 bytes
```
/J%2-z\_\~/J\o
```
[Try it online!](https://tio.run/##K6gsyfj/X99L1Ui3KiY@pk7fKyb////4@IC6/Py6/Lr4/Lq6/Ph4AA "Pyth ‚Äì Try It Online")
A port of [@GB's wonderful Ruby answer](https://codegolf.stackexchange.com/a/199033/64121), go give him your upvotes!
Terrible explanation:
```
/       \~      // Count the occurrences of "~" in:
 J              // J=
  %2            // Every second character of
    -z\_        // every character of the input not in "_"
                // Implicit print
          /J\o  // Count the occurrences of "o" in J
                // Implicit print
```
[Answer]
# Python 3.8, 62 bytes
```
lambda s:((v:=s.replace("_","")[::2]).count("o"),v.count("~"))
```
You can [try it online](https://tio.run/##K6gsycjPM7YoKPqfpmCrEPM/JzE3KSVRodhKQ6PMyrZYryi1ICcxOVVDKV5JR0lJM9rKyihWUy85vzSvREMpX0lTpwzGqVPS1PxfUJQJZKcBlcfX5dflB@SDRQE). Link has two extra bytes to give a name to the function.
Port of [this](https://codegolf.stackexchange.com/a/199033/75323) Ruby answer, so be sure to upvote it as well!
[Answer]
# [Burlesque](https://github.com/FMNSSun/Burlesque), 11 bytes
```
'_;;\[2enf:
```
[Try it online!](https://tio.run/##SyotykktLixN/f9fPd7aOibaKDUvzer///j8urr8gPi6/Pw6AA "Burlesque ‚Äì Try It Online")
Using the algorithm of [G B's answer](https://codegolf.stackexchange.com/a/199033/91386)
# Burlesque, 24 bytes
```
'P;;^p<-_+'_;;m{2co}FLf:
```
[Try it online!](https://tio.run/##SyotykktLixN/f9fPcDaOq7ARjdeWz3e2jq32ig5v9bNJ83q///4/Lq6/ID4uvz8OgA "Burlesque ‚Äì Try It Online")
Without error checking.
```
'P;;   # Split at P
^p<-   # Reverse those following the piper
_+     # Rejoin
'_;;   # Remove all road
m{2co} # Split each into pairs (i.e. mice)
FL     # Flatten array
f:     # Count mice
```
# Burlesque, 44 bytes
```
'P;;sa2!=qpPif^p<-_+'_;;m{2co}FLf:sa2!=qpPif
```
[Try it online!](https://tio.run/##SyotykktLixN/f9fPcDaujjRSNG2sCAgMy2uwEY3Xls93to6t9ooOb/WzSfNCiH7/398fl1dfkB8XX5@XQAA "Burlesque ‚Äì Try It Online")
With error checking. As above but with checks to see if lists are correct lengths and throw impossible action if not, halting execution.
[Answer]
# Jelly, ~~14~~ ~~[13](https://tio.run/##y0rNyan8///hjvmPGubGH9rqpWp0ePqR7kcb1z1qmFOX//9w@6OmNf//RyvF1@Xn1wXEx@fXKekoQHkQdl1@QF2@UiwA)~~ 10 bytes
A monadic link taking the string as input.
```
·∏ü‚Äù_m2ƒã‚±Æ‚Åæ~o
```
You can [try it online](https://tio.run/##y0rNyan8///hjvmPGubG5xod6X60cd2jxn11@f8Ptz9qWvP/f7R6fF1@fl1AfHx@nbqOApQHYdflB9Tlq8cCAA).
Port of [this](https://codegolf.stackexchange.com/a/199033/75323) Ruby answer so check it as well!
```
·∏ü‚Äù_         remove all the underscores from the string
   m2       Then take a slice modulo 2 and
                for what remains
      ‚±Æ‚Äú~o  go over the characters ~ and o
     ƒã      counting how many times they show up.
```
Output is `[towards, away]`.
*-3 bytes* thanks to @Jonathan and @Nick.
[Answer]
# [PHP](https://php.net/), 108 bytes
```
for(;$b=$argn[$j++];){$b!='P'?:$p++;$b=='~'?($p&++$j?$m++:$n++):($b!='o'?:($p&++$j?$n++:$m++));}echo"$n $m";
```
[Try it online!](https://tio.run/##RcpBCsIwEEbhq2j5MQ2DF0gM2bnuXiRYUWuhmaG6E@foxtSNm7f5ngxSdlFqrzy3Hn3Aab7lA0aio7cv9OtgOhMdhGjhYNTEFrIhwhgxETlkIuva38p1/WtetC7W@vflPHCDvMLU@FJS6pRZWROrckoflued86Ns918 "PHP ‚Äì Try It Online")
Back to more serious golfing, ends like a port of Noodle9's original answer (but much more readable)
**ORIGINAL VERSION:**
# [PHP](https://php.net/), 156 bytes
```
$a=explode('P',$argn);for($i=2;$i--;$j=0)for($b=$a[$i];$b[$j];){$t=$b[$j].$b[++$j];if($t=='~o')$i&++$j?$n++:$m++;if($t=='o~')$i&++$j?$m++:$n++;}echo"$n $m";
```
[Try it online!](https://tio.run/##TYqxCsIwGIRfRcphGmJFHI2hm3P3UkKrrabY/KF2EMQ8ujFVEJe74/vOXVzY5y4matXe3ZVObcoKtkI9ni2XHY0pjNpKmCyT6NWGf1CjUJcwlURToq8kf2BS372OJcQMTZdGqpgnxmGWM8xhhdhhEOJnyf/ZYbbxIp/t8UIJ7AJDIkPQuvBEnrwm70nrF7nJkL2F7PAG "PHP ‚Äì Try It Online")
Ok, this is really horrible and far from optimal, but I had real fun writing this unreadable atrocity. Forgive me :D (the reason behind the explode was to check validity for original post rule of only one `P` in the string)
**EDIT: ORIGINAL VERSION WITH ERROR CHECKING (displays `0` on error)**
# [PHP](https://php.net/), 213 bytes
```
$a=explode('P',$argn);for($i=0;isset($a[$i]);$j=0,++$i<3?:die(0.))for($b=$a[$i];$b[$j];){strpos(" _~o",$b[$j])?:die(0.);$t=$b[$j].$b[++$j];$t=='~o'?($i&$j++?$m++:$n++):($t!='o~'?:($i&$j++?$n++:$m++));}echo"$n $m";
```
[Try it online!](https://tio.run/##RY3BCsIwEER/RctisqRKwVtjyM2zd5FSNWqKZkOTgyDm063Rgh52F2bezPqLH1ba5w2tMnd/paPhbMNKaPuzQ3minoNVlbQhmMih3YLdoYROVaUQYFdLXR@t4dUC8cvu1chI2G@h20l8hNh7CryYNImKcpTxl5IQ1agt8smVOZMlxRIxnV/PoBNCw02IGpwQWHOIU8UoMV3/bfexM4Mon@ZwoQLcBG6FHIamobTJk@hFPlpyYZiv3w "PHP ‚Äì Try It Online")
**Caveat**: won't display the zero results, but `,$n=0,$m=0` can be added after `$i=0` to make it so.
[Answer]
# [GolfScript](http://golfscript.com), ~~46 bytes~~ 36 bytes
```
1/{"_"=!},'P'%~-1%+2/.{"~o"=},,.@,\-
```
Significant improvement from my previous algorithm. Enough so that I'm willing to actually explain it.
```
1/                                     #Split the string into an array of chars
  {"_"=!},                             #Replace the prev array with one without underscores
          'P'%~                        #Split the array at the piper
               -1%                     #Reverse the second array (right side)
                                       #This has the function of making all correct mice
                                       #face the same way, which makes for easier matching
                  +                    #Concatenate
                   2/                  #Split the array into groups of two
                                       #so we only an array of mouse-strings!
                     .                 #Duplicate our array, since we have to count twice
                      {"~o"=},,        #First count all valid mice
                               .       #Duplicate that count
                                @,     #Bring back that second array and count the mice
                                  \-   #Subtract (correct mice) from (all mice)
                                       #which only leaves (correct mice) then (wrong mice)
```
[Answer]
# [PowerShell](https://github.com/TryItOnline/TioSetup/wiki/Powershell), ~~46~~ 42 bytes
*Inspired by [G B](https://codegolf.stackexchange.com/a/199033/80745)*
```
$a=,0*7
$args|%{$a[$i++%2+$_%6]++}
$a[4,1]
```
[Try it online!](https://tio.run/##VY/dCoJAEIXv9ymGZSxtNzCLgkDwEbyXWKS2HxDG1ChQ99VtW7KfA3Mz5ztzmJLuuqrPuigGPEIM7YB5LMPZhmFenerOazHP8CKEFwlU3nonRG@tbCUXu6FnLPEZWEl/qhSZ1I6hqYRRCwlR8CVSQ2TIOEopxy1/CUMpmZ@4UyQh/BC246/AKXQ3AujAg9aRWFF@kID6Uep9ow/2M1RvR9e3orGLiX04eXFuz9Hnb4/P9ZV/ojzYjiHO@uEJ "PowerShell ‚Äì Try It Online")
```
    | ascii | %6 | even | odd
 -----------------------------
  P |   80  |  2 |   2  |  3
  _ |   95  |  5 |   5  |  6
  o |  111  |  3 |   3  |  4
  ~ |  126  |  0 |   0  |  1
```
The 4 and 1 are `odd-numbered positions` from the `G B` answer. No error checking.
---
# [PowerShell](https://github.com/TryItOnline/TioSetup/wiki/Powershell), 46 bytes
```
switch($args|?{$i++%2}){o{$t++}~{$a++}}+$t;+$a
```
[Try it online!](https://tio.run/##VY/dCsIwDIXv9xShRLfRCjrvFHGPsDcoQ6sbDDK3yoSuffVZiz/zQAicfCchLQ2q6yvVNBNe4ABm6odan6oEy@7aj0eDNeeLzKaGDGrOrTNY@mY56j3HcrJRlCcReIkklpJc4ctRLOCjjYAs/RGFI3LkAiVl4LZzwlFBbhYPygSsv4S/8XcgaB12pDDCAkwgsaPyLADVo1Unrc7@O5TviervjfbG0j@dv7jgM0zYe8ZW6sa@UZbuPiEW2ekJ "PowerShell ‚Äì Try It Online")
[Answer]
## [Unix TMG](https://github.com/amakukha/tmg), 115 bytes
```
p:ignore(<<_>>)r<P>[a=^t][t=^a][a=^t]r parse(d);r:<o~>[t++]r|<~o>[a++]r|();a:0;t:0;d:decimal(t)decimal(a)={2< >1};
```
Expanded:
```
p:ignore(<<_>>)r<P>[a=^t][t=^a][a=^t]r parse(d);
r:<o~>[t++]r|<~o>[a++]r|();
a:0;
t:0;
d:decimal(t)decimal(a)={2< >1};
```
[Answer]
# [Python 3](https://docs.python.org/3/), 86 bytes
```
m=input()
n=m.index('P')
c=count
t=m[:n].c('~o')+m[n:].c('o~')
a=m.c('~')-t
print(t,a)
```
[Try it online!](https://tio.run/##HYsxDoAgDAB3PlIalcWNhD@4EweDJjLQElMSXfg6ouPl7vIjJ9PcWnKRchGNilwykfbj1rAAquACFxIlLnlLqwkaKgMOyZP9iWuvtj59BnASla9IomXcsLUX "Python 3 ‚Äì Try It Online")
Takes in the string, and finds the location of the Piper. Then just counts the number of mice behind him facing forwards, plus the number of mice ahead of him facing backwards - this is the total number of mice facing towards him. The number of mice facing away is just the total number of mice (the total number of '~'s) minus the number facing him.
Uses c to replace the count function, for byte saving.
[Answer]
# Java 8, ~~72~~ 71 bytes
```
s->{int i=1,r[]=new int[2];for(int c:s)r[~c&1]+=c!=95?i^=1:0;return r;}
```
Port of [*@GB*'s Ruby answer](https://codegolf.stackexchange.com/a/199033/52210), so make sure to upvote him!!  
-1 byte thanks to *@Arnauld*.
[Try it online.](https://tio.run/##VVBRS8MwEH7frzj7IClzwQo@2BJFfHYU9jhqiVmmqV0yknQyRvPX6zV16AIJd993992Xa/iBL5rN1yBa7hy8cqVPMwClvbRbLiQsxzQC6woEEZ/cYuDSAuF@ho/z3CsBS9DAYHCLxxPWgmLZDRYyLb9j711VbI0lIyVyl9p1ENdZNWfiij3cP6k3luW3hZW@sxps0Q/FKL3v3luU/p1wMGoDOzRIVt4q/YE2eDq589J5ktS1CSXeYJJo7w8vgzHBhMjV9SUbTGnCJYQyZ43/X4wGYsVkALcwjV8dnZc7ajpP90j4VhM3T3JI5g2ul3ZetfTZWn501Jupl2gqyJi@4EIjR1I808h@@AE)
**Explanation:**
```
s->{               // Method with char-array parameter and int-array return-type
  int i=1,         //  Toggle integer, starting at 1
   r[]=new int[2]; //  Result int-array of size 2, filled with 0s by default
  for(int c:s)     //  Loop over the input char-array:
    r[~c&1]+=      //   Increase the count at index (c+1)%2 by:
      c!=95?       //    If the character is NOT '_':
            i^=1   //     Toggle the integer (1‚Üí0 or 0‚Üí1), and add that to the current count
                   //     this will only add 1 for every odd-indexed character, ignoring '_'
           :       //    Else:
            0;     //     Keep the count the same by increasing with 0
  return r;}       //  And finally return this resulting pair of counts
```
[Answer]
# [K (ngn/k)](https://bitbucket.org/ngn/k), 18 bytes
```
{+/2!0N 2#0,x^"_"}
```
[Try it online!](https://tio.run/##y9bNS8/7/z/Nqlpb30jRwE/BSNlApyJOKV6p9n@JVbVKdGVdkVWaQoV1Qn62tUZCWmJmjnWFdaV1kWZsLVdJtFJ8fH5dABDX5StZGyoYxULEAury8@vy68Di8fFK1sZQmbr8gPw6JWsjBQMwF6gVpM8AKPsfAA "K (ngn/k) ‚Äì Try It Online")
`{` `}` function with argument `x`
`x^"_"` remove all `_`s
`0,` prepend a `0`
`0N 2#` split in pairs
`2!` mod 2 as ascii codes: `P`‚Üí80‚Üí0, `o`‚Üí111‚Üí1, `~`‚Üí126‚Üí0
`+/` sum
[Answer]
# [C++ (gcc)](https://gcc.gnu.org/), [189](https://null.link.io/ "-5 bytes thanks to @ceilingcat") [184](https://null.link.io/ "-14 bytes when inspired by @Arnauld 's answer") 170 bytes
```
#include <string>
struct a{int t;int f;};a f(std::string s){a r={0,0};for(int i=0,d=1;i<s.length();++i)s[i]%3?s[i]%2?1:d=0:s[i++]%2?d?r.f++:r.t++:d?r.t++:r.f++;return r;}
```
[Try it online!](https://tio.run/##zZRRT9swEMff8ylum6YmTSlJQYLFDX3apD1MQhpvXVUZx2ktWjtyHLGqNF@dnZPQEloYEmIaoMR397fv/zuXsiw7mjF2/0lItigSDkOhcqM5XV44RS7kDCRd8jyjjENuEvJIiDKsXzj4LpgBuhbSgCH2mZINoZC6uCOKah3k3pqCjtdBL9iQVGnXCkUc9JI4JGKY9xdczszc9YjvCy8fi8nnk1H1GozCKImDCAPft2Ey0v3U9yPdN/i0kakizBHNTaElaLK5P@46P2@FYXO4pStwB@EJXK8Mzz2I3sl01c21pr01ozmH88A6J9c40BtSZTqqE6GWuIn3mKIlKWtJG6wWbHZ8jnPFtaR6VeOF56fvjYdccXwejJrLwABpRljqtW@kqZW72hYjCslBAmHmwOZUW46zt3FUx7CXcVicj9HbxGNbIPYcDXsdynfDNTVKP9zGl7dRWJG1bTFoYRRy5P1rPhMS7YsPGHCZNBfTFVsKuzyMUVVewREf@nHufqikITsLGrI7RDus/l@/EpzusePYJktq5whrB6DxImRWGILxjJuFkNxlQvbqrGfTaJSaKVMF7o6RY1fBnIHhcFfvV@FH/G1lU@LgeI@78PU3XWYLjiZubOdsZeZK4jEJdxKeQoZ@TKNx6wnYDxGAwMaBbahVnvNkmomMa8x9o4ucY34p8Es6HuM0JxjdzgX2EDCE@gw4gkF1DLIwI7BjjOZkopZ9@8KebtA79SqBSLcabNnsgtqZ25l2eoAfPog7Ha@pCPBjCKuAL1q7Q8DDQSrTtv3kyMv9I59SXumC/7XbYOvVDmMcTHbKimrPx1a/tVKqfS8cB7yvVOUzgxgcsnbSthY@tfZvbL0wg/ZVNJub5C@J2WakvQcAD/@d7lWpylLZ53Rary5xraY2ntoVrvGvWtr6Hw "C++ (gcc) ‚Äì Try It Online")
Expanded Version (Full Program) : 
```
// Example program
#include <iostream>
#include <string.h>
using namespace std;
struct pseudo_arr {int to_piper; int from_piper;};
pseudo_arr countRats(string s) {
  pseudo_arr rats = {0,0};
  int direction = 1;
  for(auto i = s.cbegin();i!=s.cend();++i) {
    // Exploitable properties of the 4 characters
    // 'P' == 80  - %3 == 2, %3 == 0
    // '_' == 95  - %3 == 2, %2 == 1
    // '~' == 126 - %3 == 0, %2 == 0
    // 'o' == 111 - %3 == 0, %2 == 1 
    switch(*i) {
      case 'P' : // char(80) == 'P'
        direction = 0; // Crossed piper, change direction
        break;
      case 'o' :
        // If see head, skip tail
        ++i;
        // if before piper then away, else towards
        direction ? rats.from_piper++ : rats.to_piper++;
        break;
      case '~' :
      // if see tail, skip head
        ++i;
        // if before piper then towards, else away
        direction ? rats.to_piper++ : rats.from_piper++;
        break;
    }
  }
  return rats;
}
int main() {
  string input;
  getline(cin, input);
  pseudo_arr rat_count = countRats(input);
  cout << rat_count.to_piper << " " << rat_count.from_piper;
}
```
[Answer]
# [Z80Golf](https://github.com/lynn/z80golf), 28 bytes
```
00000000: 1680 cd03 8030 0578 ff79 ff76 fe5f 28f0  .....0.x.y.v._(.
00000010: 1930 ed0c fe7e 28e8 0d04 18e4            .0...~(.....
```
[Try it online!](https://tio.run/##rYw7DgIxDER7TjHlVpbDfuLlFHsDF5uEBskdAgpfPSRAwQH2jTTVzHsJX@1WauUfF4RFGHviEcIjg@coKCWuvRaUPBecpTBAHaYHPelOOtDpawjdsbZnTry3fcxtnwWceEKQPOGP9ify4aOqVXVzMzdXczdVt2NykMbf "Z80Golf ‚Äì Try It Online")
```
start:
  ld d, $80
  call $8003
  jr nc, ok
results:
  ld a, b
  rst $38
  ld a, c
  rst $38
  halt
ok:
  cp '_'
  jr z, start
  add hl, de
  jr nc, start
  inc c
  cp '~'
  jr z, start
  dec c
  inc b
  jr start
```
Prints two bytes: `towards` and `away`.
One maybe-clever trick here is using `add hl, de` as a sort of flip-flop mechanism. Since `de` is fixed to `$8000`, it will overflow and set the carry flag every other time.
]