text:
Reverse sentences
The goal of this challenge is to receive an input and output that input but with sentence order reversed.
Example Input:
Hello friend. What are you doing? I bet it is something I want to do too!

Example Output:
I bet it is something I want to do too! What are you doing? Hello friend.

As you can tell from the examples, your program has to deal with question marks, exclamation points, and periods. You can assume each sentence has a punctuation and than a space before the next sentence. Trailing spaces/newlines are ok, as long as it is readable.
Shortest code wins.
Good luck!
EDIT: You can assume the sentences has no quotes or parentheses, but if you make your code be able to deal with both of those then you get -5 bytes Example output for parens/quotes:
"Hello, " she said. (I didn't know what she was talking about.) --> (I didn't know what she was talking about.) "Hello, " she said.

Can we assume that there aren't going to be any quotes or parentheses? If not, how do we handle them?

Made an edit to the post clearing that up.

Can you give an example of expected output for a sentence containing quotes or parens, please?

Added an edit with an example sentence for those.

If a sentence has punctuation within quotes or parens, how should we deal with it?

What about internal abbreviations, like Mr.?  Also, what if an input is "Hello!" she said.  (I hesitated.  How should I respond?  This is too much!) I responded, "How are you?" without thinking any more about it.

What about a sentence containing "i.e." and the like?

Was wondering why no one challenge this using VB.Net????

@Scimonster You mean "i.e.", etc., right?  Oh, and please amend my test case quote to be: "Hello!" she said. (I hesitated. How should I respond? This is too much!) I responded, "Hi there. How are you? What is your cat's name?" without thinking any more about it.

You did your grammar wrong. It should be "Hello," she said.. Notice the comma inside the quotes.

Still incorrect. The whole example should be changed to "Hello," she said. (I didn't know what she was talking about.) --> (I didn't know what she was talking about.) "Hello," she said.

Can we assume that the sentences have no linefeeds?

Julia, 45 42 bytes - 5 bonus = 37
s->join(reverse(split(s,r"[.?!]\K "))," ")

This creates an anonymous function that accepts a string as input and returns the string with its sentences reversed. This handles any special character appropriately, though double quotes and dollar signs must be escaped, otherwise they aren't valid strings in Julia.
Ungolfed + explanation:
function f(s)
    # Get individual sentences by splitting on the spaces that
    # separate them. Spaces are identified by matching punctuation
    # then moving the position beyond that match and matching a
    # space. This is accomplished using \K.

    sentences = split(s, r"[.?!]\K ")

    # Reverse the order of the array of sentences.

    reversed_order = reverse(sentences)

    # Join the array elements into a string, separated by a space.

    join(reversed_order, " ")
end

Examples:
julia> f("Hello friend. What are you doing? I bet it is something I want to do too!")
"I bet it is something I want to do too! What are you doing? Hello friend."

julia> f("\"Hello, \" she said. (I didn't know what she was talking about.)")
"(I didn't know what she was talking about.) \"Hello, \" she said."

And if you don't like looking at the escaped quotes in the output:
julia> println(f("\"Hello, \" she said. (I didn't know what she was talking about.)"))
(I didn't know what she was talking about.) "Hello, " she said.

Saved 3 bytes on the regular expression thanks to Martin Büttner! Previously this used a lookbehind: (?<=[.?!]).

I don't think that this qualifies for the bonus...

@Optimizer: How does it not? It works as expected with parentheses, quotes, etc. as given in the post.

Can you provide an online link to test , with the example from the bonus section of the question.

@Optimizer: The only way to run a recent version of Julia online requires registration and doesn't support permalinks. Would it suffice to simply include input and output here in the post?

Sure, I guess..

@Optimizer: Okay, examples added.

CJam, 23 22 bytes
I am not sure if this qualifies for the bonus or not, but here goes the solution:
Sq{1$".?!"-{])[}|}%]W%

Code Expansion (bit outdated):
Sq+                      e# Read the input and prepend with a space
   {            }%       e# For each input character
    _".?!"&              e# Copy and check if its one of ., ? and !
           {][}&         e# If it is one of the above, wrap everything till now in an array
                         e# and start a new array to be wrapped next time we get one of those
                         e# three characters. We now have an array of strings, each having
                         e# a single sentence
                  W%     e# Reverse the ordering of these sentences
                    s(   e# Convert to string and remove the first space

Try it online here

Ah, you made this post right after I edited it at first. You get a -5 bonus now (Just to make it a little harder)
So -5 bonus to you! 18 bytes, wow, not sure if thats beatable :P

J, 35 32
It almost handles bonus input, except I have to escape single apostrophes, so I guess it doesn't count. (Also, my first submission here)
f=.;@|.@(]<;.2~'.?!'e.~])@,~&' '

Usage:
f 'Hello friend. What are you doing? I bet it is something I want to do too!'

Perl, 27/25
#!perl -n
print reverse/ |[^.!?]*./g

Or from the command line:
$perl -nE'say reverse/ |[^.!?]*./g'

Nice! You can get the -5 bonus with perl -nE 'say reverse/ |[^.?!]*.\)?/g', bringing your total count to 23.

PHP, 60
echo join(' ',array_reverse(preg_split('/(?<=[?!.])/',$s)));

Can you use the regex [?!.]\K instead?

Also doesn't this add additional spaces into the string unless you include the space in the pattern to split by?

@MartinBüttner, no, I won't able to restore the proper sign when joining data back, so we need something which won't consume the character.

Bash + coreutils, 40 bytes
sed 's/\([?.!]\) */\1\n/g'|tac|tr \\n \

This reads from STDIN so input may me redirected in from a file, or simply piped in, e.g.:
$ printf 'Hello friend. What are you doing? I bet it is something I want to do too!' | sed 's/\([?.!]\) */\1\n/g'|tac|tr \\n \
I bet it is something I want to do too! What are you doing? Hello friend.
$

Does this really work for parentheses in the sense, that (foo bar.) gets swapped as a unit?

@MartinBüttner Looks like the question got edited, so I can no longer claim the bonus :(

Pip, 25 bytes
a.:sRV(a^@2+$ALa@*^".?!")

After appending a space to the input string, we find all indices of ., ?, and !, add 2, and use the ^@ split-at operator to break the string into sentences (each with a trailing space). Reverse the list, and it's auto-printed at the end of the program.  Voilà!
Example showing the stages of the main computation with input A! B? C. D!:
              ^".?!"     ["." "?" "!"]
           a@*           [[7] [4] [1 10]]
        $AL              [7 4 1 10]
      2+                 [9 6 3 12]
   a^@                   ["A! " "B? " "C. " "D! "]
RV(                 )    ["D! " "C. " "B? " "A! "]

                         D! C. B? A!

No you don't :)

Retina, 61 34 33 30 bytes
Credits to nutki for cutting this down by 24 bytes.
^
#
+`(#.*[.!?]) (.+)
$2 $1
#
<empty>

Where <empty> stands for an empty line. This assumes that # is not part of the input, but if that's not legitimate, I could swap it out for any other character, including " (which I'd only need to handle for the bonus) or something unprintable. You can run the code like that in a single file if you use the -s flag, or you can put each line in a separate file and pass them all to Retina.
Reversing this with a single regex replacement is possible, but really cumbersome. Even with .NET balancing groups I needed something around 90 bytes, so instead I tried doing it in multiple steps.
In Retina, every pair of lines is one replacement stage, where the first line is the pattern and the second line is the replacement.
^
#

This stage simply prepares the string for further processing. It prepends a # as a marker. This marker indicates that everything in front of it has already been put in the right place, and everything after it still needs to be processed.
+`(#.*[.!?]) (.+)
$2 $1

This stage swaps the sentences, by repeatedly moving the last sentence in front of the # (which moves forwards through the string in the process). The +` instructs Retina to repeat this stage until the output stops changing. As an example, here is how the input foo. bar! blah? would be processed:
#foo. bar! blah?
blah? #foo. bar!
blah? bar! #foo.

And finally we simply remove the marker:
#
<empty>

Why not just .+ => $0 # and repeated (.*?[.!?] )(.*#) => $2$1?

@nutki Oh, that's much nicer, thank you. :)

JavaScript (ES6) 47 45
As it's stated, it's a simple regex exercise. In javascript:

// ES6 - FireFox only
F=t=>t.match(/\S[^.!?]+./g).reverse().join(' ')

// ES5 - so much longer
function G(t){return t.match(/\S[^.!?]+./g).reverse().join(' ')}

// TEST

alert(G("Hello friend. What are you doing? I bet it is something I want to do too!"))

I was going to do javascript, but you beat me to it.

This produces extra spaces before all but the last sentence (originally the first). Not sure if it is OK, as the task is not very well defined.

@nutki yes, I agree. Fixed

Python 2, 62
Not going to improve for the bonus, as it's probably not worth the byte cost.
import re
print' '.join(re.split('(?<=[?!.]).',input())[::-1])

This does not qualify for the bonus. Look at the bonus example in the question

@Optimizer Look in the question history. At the time I updated my question to add the bonus, my output matched the example. There was nothing indicating that parenthesis could be outside of a period.

I think the intention was this only from the beginning. A solid example came later though. Doesn't mean that you still get the bonus :) (I removed mine too)

Java, 113
s->{String t[]=s.split("(?<=[\\.?!]) "),u="";for(int i=t.length;i-->0;)u+=t[i]+" ";return u.replaceAll(".$","");}

Ruby, 48(42 without the puts) bytes
reverse_sentence.rb
puts $*[0].scan(/\S[^.!?]+./).reverse.join(" ")

Usage:
ruby reverse_sentence.rb 'Hello friend. What are you doing? I bet it is something I want to do too!'

Output:
I bet it is something I want to do too! What are you doing? Hello friend.

Criticism more than welcome.

Criticism: You spelled "sentence" incorrectly.

save 6 characters: .join(" ") => *" "

@AlexA. Best feedback ever!

@daniero thanks, nice to know

Matlab (93 bytes)
y=[32 input('','s')];y=sortrows([cumsum(ismember(y,'?!.'),'reverse');y]',1)';disp(y(4:2:end))

This assumes the input doesn't contain leading or trailing spaces
Uses standard input and output
Tested in Matlab 2014b

Ruby 41
The other Ruby answers don't have enough WTF.
#!ruby -apF(?<=[.!?])\s
$_=$F.reverse*" "

This at least works in Ruby 2. If the a and F switch works in 1.8.7, I guess you could drop $_= to save three characters.
Reverses every line on stdin and print to stdout:
$ ruby foo.rb <<< "Hello. Hi. How are you? Good, you? fine, thanks."
fine, thanks. Good, you? How are you? Hi. Hello.

Could you please explain the answer.

k, 31
{1_,/|(0,1+&x in"?!.")_x:" ",x}

.
k){1_,/|(0,1+&x in"?!.")_x:" ",x} "Hello friend. What are you doing? I bet it is something I want to do too!"
"I bet it is something I want to do too! What are you doing? Hello friend."

C# - LINQPAD - 93 - 5 = 88 bytes
void Main(){string.Join(" ",Regex.Split(Console.ReadLine(),"(?<=[.?!]) ").Reverse()).Dump();}

C# Console App 189 - 5 = 184 bytes
using System;using System.Linq;using System.Text.RegularExpressions;class P{static void Main(){Console.WriteLine(string.Join(" ",Regex.Split(Console.ReadLine(), "(?<=[.?!]) ").Reverse()));}}

regex shamelessly flogged from Alex A. :)

You can save 7 bytes by putting your application in namespace System then within that using Linq;usingText.RegularExpressions saving 2x system.

I don't think that this qualifies for the bonus. Look at the bonus example in the question

Clojure - 44 71 chars
(defn rs[s](reverse(re-seq #"\S.+?[.!?]"s)))

Improved and simplified RE, eliminated unnecessary whitespace.
Output is a sequence of the sentences in the original string, with the order of the sentences reversed:
Input: "Hello friend. What are you doing? I bet it is something I want to do too!"
Output: ("I bet it is something I want to do too!" "What are you doing?" "Hello friend.")

Ruby, 47
$><<gets.strip.split(/(?<=[.?!]) /).reverse*' '

credits to Martin Büttner, for saving some characters.

You can read the input from STDIN with gets to save a byte, print it with $><< to save byte (no need for a space) and join the string with *'' to save two bytes.

@MartinBüttner thanks for the suggestion, I wouldn't go with reading from the input from STDIN, though. Simply because there will be a trailing new line.

Actually, I think your code will currently result in a leading space.

mmm, you're right. I'll see what should I do.

CJam, 21 bytes
1q{1?_"!.?"-}%1a/W%S*

This works by turning spaces after !s, .s and ?s into the number 1 (not the character 1 nor the character with code point 1, so the input can still contain those), splitting at 1's, reversing the order of the resulting chunks and joining by spaces.
Try it online in the CJam interpreter.
How it works
1                     e# B := 1
 q                    e# Q := input()
  {         }%        e# for each C in Q (map):
   1?                 e#   C := B ? C : 1
     _"!.?"-          e#   B := string(C).strip("!.?")
              1a/     e# Q := Q.split([1])
                 W%   e# Q := reverse(Q)
                   S* e# Q := Q.join(" ")
                      e# print(Q)

source: Stack Exchange

license: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/3.0/

sort: votes


text:
Optimize the Scralphabet
Scralphabet
A normal bag of Scrabble tiles contains the following letters (? is a blank tile, which can stand for any other letter):
AAAAAAAAABBCCDDDDEEEEEEEEEEEEFFGGGHHIIIIIIIIIJKLLLLMMNNNNNNOOOOOOOOPPQRRRRRRSSSSTTTTTTUUUUVVWWXYYZ??

The letters have the following value:
{"A": 1,"B": 3,"C": 3,"D": 2,"E": 1,"F": 4,"G": 2,"H": 4,"I": 1,"J": 8,"K": 5,"L": 1,"M": 3,"N": 1,"O": 1,"P": 3,"Q": 10,"R": 1,"S": 1,"T": 1,"U": 1,"V": 4,"W": 4,"X": 8,"Y": 4,"Z": 10,"?": 0}

Given a normal bag of Scrabble tiles, construct the highest-scoring set of non-intersecting words (i.e., individual words, not on a Scrabble board) given the following conditions:

The score for each word is sum(letter_values) * length(word).
You may only include a maximum of one word starting with each letter of the alphabet (so, a maximum of 26 words).
Only valid Scrabble words (from this dictionary) may be included. You may read the dictionary from a file, hard-code it (ugh), or scrape it from the website.
You need not use every tile, but all unused tiles form a single word, scored the same way, which subtracts from your score.

If you wish, your code may accept two inputs: the bag contents as a string, and the letter values in some format similar to a python dict (as above); alternatively, you can hard-code the bag contents and letter values. It should output the words in your set, their respective scores, and your total score, in some reasonable format.
Highest scoring set of words wins, with ties going to first posted.

Can the valid Scrabble word dictionary be hardcoded as well?

Also, what if my program is print"FOO18\nBAR15\nBAZ42\n...\n1523"?

@Mauris Hardcoding the output is a banned loophole.

@Geobits he says you can though. "alternatively, you can hard-code the values".

@Tim The OP is referring to the input.

@Geobits It's not that simple though. There are many forms of "hardcoding" (like simplifying the search space if you already know what you'll find). Or you could write a really elaborate code to find the optimal solution, and then replace it by a brute force for golfing.

@MartinBüttner Yea, my reply was to bare hardcoding, as Mauris was suggesting here.

@Mauris you can if you want...? I'd rather you read it from a file, though, to make the code more readable. And, yes, hardcoding your output is a banned loophole.

And if someone posts a golfed brute-force, I hope they'll also post the algorithm that led to their solution.

As far as I know, the normal rule for [code-challenge] is that the code you post must generate the output you post. If someone posts a brute force that is obviously unfeasible to run within years, along with an optimized output, I think the people here are smart enough to see through that.

@Geobits: Speak for yourself. :P

Pro tip: Be careful with how you handle the full Scrabble dictionary. I was working on a solution in R and merging the words with their scores used all available memory and crashed my computer.

Question about the scoring: "A" scores 1 * 1 = 1, while "ABC" scores (1 + 3 + 3) * 3 = 21?  Is this correct?

yes, that's correct.

C, 2765 (optimal)
Edit
Now all in a single C file. This just finds all the optimal solutions. They all must have 6 words of 15 letters and one 10-letter word consisting of 8 letters of value 1 and two blanks. For that I only need to load a fraction of the dictionary and I don't have to look for 15 letter words with blanks.
The code is a simple exhaustive depth-first search.
#include <stdio.h>
#include <stdint.h>
#include <string.h>
struct w {
    struct lc { uint64_t hi,lo; } lc;
    char w[16];
} w15[6000], w10[40000];
int n15,n10;
struct lc pool = { 0x12122464612, 0x8624119232c4229 };
int pts[27] = {0,1,3,3,2,1,4,2,4,1,8,5,1,3,1,1,3,10,1,1,1,1,4,4,8,4,10};
int f[27],fs[26], w15c[27],w15l[27][6000];
int count(struct lc a, int l) { return (l < 16 ? a.lo << 4 : a.hi) >> 4*(l&15) & 15; }
int matches_val(uint64_t a, uint64_t b) {
    uint64_t mask = 0x1111111111111111ll;
    return !((a - b ^ a ^ b) & mask);
}
int matches(struct lc all, struct lc a) { return matches_val(all.hi,a.hi) && matches_val(all.lo,a.lo); }
int picks[10];
void try(struct lc cur, int used, int level) {
    int c, i, must;
    if (level == 6) {
    for (i = 0; i<27; i++) if (count(cur, i) && pts[i]>1) return;
    for (i = 0; i < n10; i++) if(!(used & (1 << (w10[i].w[0] & 31))) && matches(w10[i].lc, cur)) {
        for (c = 0; c<level; c++) printf("%s ",w15[picks[c]].w);
        printf("%s\n",w10[i].w);
    }
    return;
    }
    for (i = 0; i < 26;i++) if (count(cur,fs[i])) break;
    must = fs[i];
    for (c = 0; c < w15c[must]; c++) { i = w15l[must][c]; if(!(used & (1 << (w15[i].w[0] & 31))) && matches(cur, w15[i].lc)) {
    struct lc b = { cur.hi - w15[i].lc.hi, cur.lo - w15[i].lc.lo };
    picks[level] = i;
    try(b, used + (1 << (w15[i].w[0] & 31)), level+1);
    }}
}
int cmpfs(int *a, int *b){return f[*a]-f[*b];}
void ins(struct w*w, char *s, int c) {
    int i;
    strcpy(w->w,s);
    for (;*s;s++)
    if (*s&16) w->lc.hi += 1ll << 4*(*s&15); else w->lc.lo += 1ll << 4*(*s&15) - 4;
    if (c) for (i = 0; i < 27;i++) if (count(w->lc,i)) f[i]++, w15l[i][w15c[i]++] = w-w15;
}
int main() {
    int i;
    char s[20];
    while(scanf("%s ",s)>0) {
    if (strlen(s) == 15) ins(w15 + n15++,s,1);
    if (strlen(s) == 10) ins(w10 + n10++,s,0);
    }
    for (i = 0; i < 26;i++) fs[i] = i+1;
    qsort(fs, 26, sizeof(int), cmpfs);
    try(pool, 0, 0);
}

Usage:
$time ./scrab <sowpods.txt
cc -O3    scrab.c   -o scrab
JUXTAPOSITIONAL DEMISEMIQUAVERS ACKNOWLEDGEABLY WEATHERPROOFING CONVEYORIZATION FEATHERBEDDINGS LAURUSTINE
JUXTAPOSITIONAL DEMISEMIQUAVERS ACKNOWLEDGEABLY WEATHERPROOFING CONVEYORIZATION FEATHERBEDDINGS LUXURIATED
JUXTAPOSITIONAL DEMISEMIQUAVERS ACKNOWLEDGEABLY WEATHERPROOFING CONVEYORIZATION FEATHERBEDDINGS LUXURIATES
JUXTAPOSITIONAL DEMISEMIQUAVERS ACKNOWLEDGEABLY WEATHERPROOFING CONVEYORIZATION FEATHERBEDDINGS ULTRAQUIET
JUXTAPOSITIONAL DEMISEMIQUAVERS ACKNOWLEDGEABLY WEATHERPROOFING CONVEYORIZATION FEATHERBEDDINGS UTRICULATE
JUXTAPOSITIONAL DEMISEMIQUAVERS WEATHERPROOFING ACKNOWLEDGEABLY CONVEYORIZATION FEATHERBEDDINGS LAURUSTINE
JUXTAPOSITIONAL DEMISEMIQUAVERS WEATHERPROOFING ACKNOWLEDGEABLY CONVEYORIZATION FEATHERBEDDINGS LUXURIATED
JUXTAPOSITIONAL DEMISEMIQUAVERS WEATHERPROOFING ACKNOWLEDGEABLY CONVEYORIZATION FEATHERBEDDINGS LUXURIATES
JUXTAPOSITIONAL DEMISEMIQUAVERS WEATHERPROOFING ACKNOWLEDGEABLY CONVEYORIZATION FEATHERBEDDINGS ULTRAQUIET
JUXTAPOSITIONAL DEMISEMIQUAVERS WEATHERPROOFING ACKNOWLEDGEABLY CONVEYORIZATION FEATHERBEDDINGS UTRICULATE
OVERADJUSTMENTS QUODLIBETARIANS ACKNOWLEDGEABLY WEATHERPROOFING EXEMPLIFICATIVE HYDROGENIZATION RUBIACEOUS
OVERADJUSTMENTS QUODLIBETARIANS WEATHERPROOFING ACKNOWLEDGEABLY EXEMPLIFICATIVE HYDROGENIZATION RUBIACEOUS

real    0m1.754s
user    0m1.753s
sys 0m0.000s

Note every solution is printed twice because when adding a 15-letter 'W' word 2 orders are created because there are 2 'W' tiles.
The first solution found with the point breakdown:
JUXTAPOSITIONAL 465
DEMISEMIQUAVERS 480
ACKNOWLEDGEABLY 465
WEATHERPROOFING 405
CONVEYORIZATION 480
FEATHERBEDDINGS 390
LAURUSTINE (LAURU?TI?E) 80
no tiles left

Edit: explanation
What makes searching the entire space possible? While adding a new word I only take into account words that have the rarest remaining letter. This letter need to be in some word anyway (and a 15 letter word since this will be a non 1-value letter, though I don't check for that). So I start with words containing J, Q, W, W, X, Z which have counts around 50, 100, 100, 100, 200, 500. At lower levels I get more cutoff because some words are eliminated by the lack of letters. Breadth of the search tree at each level:
0: 1
1: 49
2: 3046
3: 102560
4: 724040
5: 803959
6: 3469

Of course a lot of cutoff is gained by not checking non-optimal solutions (blanks in 15 letter words or shorter words). So it is lucky that 2765 solution can be achieved with this dictionary (but it was close, only 2 combinations of 15 letter words give a reasonable leftover). On the other hand it is easy to modify the code to find lower scoring combinations where not all the leftover 10 letters are 1-valued, though it would be harder to prove this would be an optimal solution.
Also the code shows classic case of premature optimization. This version of matches function makes the code only 30% slower:
int matches(struct lc all, struct lc a) {
    int i;
    for (i = 1; i < 27; i++) if (count(a, i) > count(all, i)) return 0;
    return 1;
}

I even figured out how to make the bit magic parallel comparison even shorter than in my original code (highest nibble cannot be used in this case, but this is not a problem, as I only need 26 out of 32 nibbles):
int matches_val(uint64_t a, uint64_t b) {
    uint64_t mask = 0x1111111111111111ll;
    return !((a - b ^ a ^ b) & mask);
}

But it gives zero advantage.
Edit
Writing the explanation above I realized that most of the time is spent on scanning the list of words for those containing a specific letter not in the matches function. Calculating the lists upfront gave 10x speedup.

Nice! Question, how do you know that "[The optimal solutions] all must have 6 words of 15 letters and one 10-letter word consisting of 8 letters of value 1 and two blanks."?

@Claudiu, Each letter should score maximum possible multiplier which is 15 as this is the maximum word length. It is not possible to have all words of that length since the total letter count is not divisible by 15. So some letters will have a smaller multiplier. It is better to make them the cheapest letters (which are blanks and ones). The last thing is why having exactly one word shorter than 15 and not for example (5x15, 14, 11) is better, but this can also be proven to always score lower.

alrighty, since this is the highest possible score, posted first, i'm going to accept this. nice work (everyone)!

Python 2, score: 1840 2162
This program first finds the best scoring word available with the given tiles (without using wildcards), then makes 10000 attempts to include random words that meet the constraints of unique first character and having available tiles. With the current constants, the program takes 27 seconds to run on my machine. Using larger constants would probably find a higher scoring combination of words.
UPDATE: Now uses a 2 stage selection algorithm, so it finds the best of 50 words at each select stage. The penalty score is now used in the evaluation algorithm too.
from random import *

tilelist = ('AAAAAAAAABBCCDDDDEEEEEEEEEEEEFFGGGHHIIIIIIIIIJKLLLLMM'
        'NNNNNNOOOOOOOOPPQRRRRRRSSSSTTTTTTUUUUVVWWXYYZ??')
maintiles = dict((t, tilelist.count(t)) for t in set(tilelist))
value = {"A": 1,"B": 3,"C": 3,"D": 2,"E": 1,"F": 4,"G": 2,"H": 4,"I": 1,
        "J": 8,"K": 5,"L": 1,"M": 3,"N": 1,"O": 1,"P": 3,"Q": 10,"R": 1,
        "S": 1,"T": 1,"U": 1,"V": 4,"W": 4,"X": 8,"Y": 4,"Z": 10,"?": 0}
words = open('words.txt', 'rt').read().split()

def sumpoints(word):
    return len(word) * sum(value[c] for c in word)

ranked = sorted((sumpoints(w),w) for w in words)[::-1]
for points,word in ranked:
    if all(word.count(ch) <= maintiles[ch] for ch in word):
        firstword = word
        break

def findwordset(first):
    tiles = maintiles.copy()
    startletter = set(tilelist) - {'?'}
    startletter.discard(first[0])
    result = [ (first, sumpoints(first)) ]
    thistotal = sumpoints(first)
    for ch in first:
        tiles[ch] -= 1
    for i in range(30):
        best = None
        for word in sample(words, 50):
            if word[0] in startletter:
                if all(word.count(ch) <= tiles[ch] for ch in word):
                    points = sumpoints(word)
                    if best == None or points > best:
                        best, bestword = points, word
        if best:
            thistotal += best
            result.append( (bestword,best) )
            startletter.discard(bestword[0])
            for ch in bestword:
                tiles[ch] -= 1
    penaltyword = ''.join(c*n for c,n in tiles.items())
    penalty = sumpoints(penaltyword)
    return thistotal - penalty, result, tiles

best = None
for attempt in range(10000):
    wordset = findwordset(firstword)
    if best == None or wordset > best:
        best = wordset

total, result, tiles = best
penaltyword = ''.join(c*n for c,n in tiles.items())
penalty = sumpoints(penaltyword)
for word,points in result:
    print '%20s%6s' % (word, points)
print 'Remaining word "%s" penalty = %s' % (penaltyword, -penalty)
print 'Total score = %s' % total

I include here the best of a few runs:
$ python s.py
 OXYPHENBUTAZONE   615
   LIQUEFACTIONS   351
  DETERMINATIVES   280
   FAMILIARISERS   234
     JUNKETEERED   253
      WOODPIGEON   170
           GAYAL    45
         CLAUGHT    91
       BRIARWOOD   135
Remaining word "V??" penalty = -12
Total score = 2162

Note that I do not use the wild cards and pay a larger penalty (due to word length). A future enhancement may include wildcard use.

The length of the words are important: "The score for each word is sum(letter_values) * length(word)".

It's not using Scrabble scoring? Aargh.

Wow. The best mine has found so far is a score of 11371. If you multiply your score by the length (97) you get 209714.

@Tim it's on a word-by-word basis, not the total.

@sirpercival yes, but 615* 15 + 351*13... is the same isn't it?

I'm probably missing something, but why can't you make a final word from "V??"? There are quite a few that fit the bill...

My algorithm does not consider blanks "?" at all, so the remaining word will always have a "??" in it.

Simulated annealing (score 2246)
180     ADDITIVELY
338     ERYTHROPHOBIA
345     FLAGELLOMANIACS
435     INTERSUBJECTIVE
171     KOWTOWERS
390     QUADRINGENARIES
250     WEAPONIZED
200     XENOGAMOUS
-9      for blank used as S
-9      for blank used as W
-18     FTU unused
Total score: 2246

Unfortunately this is non-deterministic. I'll try to fix that and find a deterministic seed which gives a better value.
import java.io.*;
import java.util.*;

public class PPCG50219 {
    // Plus two wildcards
    private static String CHAR_FREQ  = "9224<232911426821646422121";
    private static String CHAR_VALUE = "1332142418513113:11114484:";

    private static List<List<String>> WORDS;

    public static void main(String[] args) {
        init();

        Random rnd = new Random(1);
        FeasibleSolution initial = new FeasibleSolution();
        List<List<String>> shuffledByLetter = new ArrayList<List<String>>(WORDS);
        Collections.shuffle(shuffledByLetter,  rnd);
        for (List<String> list : shuffledByLetter) {
            Collections.shuffle(list, rnd);
            for (String word : list) {
                if (initial.canUse(word)) {
                    initial.use(word);
                    break;
                }
            }
        }

        FeasibleSolution best = anneal(initial, rnd);
        System.out.println(best.toStringDetailed());
    }

    private static void init() {
        try {
            WORDS = new ArrayList<List<String>>(26);
            for (int i = 0; i < 26; i++) WORDS.add(new ArrayList<String>());

            // Take dictionary from stdin with fallback to hard-coded path.
            BufferedReader br = new BufferedReader(new InputStreamReader(System.in, "ISO-8859-1"));
            if (!br.ready()) {
                br.close();
                br = new BufferedReader(new InputStreamReader(new FileInputStream("/home/pjt33/notes/dict/sowpods"), "ISO-8859-1"));
            }

            String line;
            FeasibleSolution soln = new FeasibleSolution();
            while ((line = br.readLine()) != null) WORDS.get(line.charAt(0) - 'A').add(line);
            br.close();
        }
        catch (IOException ioe) {
            throw new RuntimeException(ioe);
        }
    }

    public static FeasibleSolution anneal(FeasibleSolution feasibleSolution, Random rnd)
    {
        //Random rnd = new Random();

        FeasibleSolution best = feasibleSolution;
        int bestScore = best.score();
        double temperature = bestScore / 10;

        FeasibleSolution current = best;
        int currentScore = bestScore;

        for (int i = 0; i < 1024; i++)
        {
            // Try out some random changes, and then adjust the temperature according to the results.
            FeasibleSolution bestAtT = current;
            for (int j = 0; j < 256; j++)
            {
                FeasibleSolution neighbour = current.randomNeighbour(rnd);
                int score = neighbour.score();

                // Use a simple threshold rather than a Boltzmann probability
                if (score >= currentScore - temperature)
                {
                    current = neighbour;
                    currentScore = score;
                    temperature *= 0.95;
                }
                if (score > bestScore)
                {
                    best = neighbour;
                    bestScore = score;
                }
            }

            if (current == bestAtT) temperature *= 1.01;
            if (temperature < 1E-6 * bestScore) break;
        }

        return best;
    }

    static class FeasibleSolution {
        private final String[] words;
        private int blanksUsed;
        private final int[] counts;

        private FeasibleSolution(String[] words) {
            this.words = words;

            counts = new int[26];
            for (String word : words) {
                if (word == null) continue;
                for (char ch : word.toCharArray()) counts[ch - 'A']++;
            }
            for (int i = 0; i < 26; i++) {
                int limit = CHAR_FREQ.charAt(i) - '0';
                if (counts[i] > limit) blanksUsed += counts[i] - limit;
            }
            if (blanksUsed > 2) throw new IllegalArgumentException("Required " + blanksUsed + " blanks");
        }

        public FeasibleSolution() {
            this(new String[26]);
        }

        public FeasibleSolution(FeasibleSolution copy) {
            this(copy.words.clone());
        }

        public boolean canUse(String word) {
            int offset = word.charAt(0) - 'A';

            String current = clear(offset);
            boolean rv = set(offset, word);

            clear(offset);
            if (!set(offset, current)) throw new IllegalStateException();

            return rv;
        }

        public void use(String word) {
            int offset = word.charAt(0) - 'A';
            clear(offset);
            if (!set(offset, word)) throw new IllegalArgumentException();
        }

        private boolean set(int offset, String word) {
            if (words[offset] != null) throw new IllegalStateException();

            if (word != null) {
                for (char ch : word.toCharArray()) {
                    int limit = CHAR_FREQ.charAt(ch - 'A') - '0';
                    counts[ch - 'A']++;
                    if (counts[ch - 'A'] > limit) blanksUsed++;
                }
            }

            words[offset] = word;
            return blanksUsed <= 2;
        }

        private String clear(int offset) {
            String word = words[offset];
            if (word != null) {
                for (char ch : word.toCharArray()) {
                    int limit = CHAR_FREQ.charAt(ch - 'A') - '0';
                    if (counts[ch - 'A'] > limit) blanksUsed--;
                    counts[ch - 'A']--;
                }
            }

            words[offset] = null;
            return word;
        }

        public int score() {
            int score = 0;

            List<List<Integer>> lengths = new ArrayList<List<Integer>>();
            for (int i = 0; i < 26; i++) lengths.add(new ArrayList<Integer>());
            int unused = 100;

            for (String word : words) {
                if (word == null) continue;
                for (char ch : word.toCharArray()) lengths.get(ch - 'A').add(word.length());
                unused -= word.length();
            }

            for (int i = 0; i < 26; i++) {
                int limit = CHAR_FREQ.charAt(i) - '0';
                int off = 0;
                List<Integer> l = lengths.get(i);
                if (l.size() > limit) {
                    off = l.size() - limit;
                    Collections.sort(l);
                }
                else if (l.size() < limit) {
                    int surplus = limit - l.size();
                    l.add(-surplus * unused);
                }
                for (; off < l.size(); off++) score += l.get(off) * (CHAR_VALUE.charAt(i) - '0');
            }
            return score;
        }

        public FeasibleSolution randomNeighbour(Random rnd) {
            FeasibleSolution soln = new FeasibleSolution(this);

            // Shake things up.
            List<Integer> used = new ArrayList<Integer>();
            int totalCount = 0;
            for (int i = 0; i < words.length; i++) {
                if (words[i] == null) continue;
                used.add(i);
                totalCount += words[i].length();
            }
            if (totalCount > 50) {
                int offset = used.get(rnd.nextInt(used.size()));
                soln.clear(offset);
            }

            // TODO We can probably get better results by biasing the shuffle.
            List<List<String>> shuffledByLetter = new ArrayList<List<String>>(WORDS);
            String theBitThatMatters = Arrays.toString(counts);
            Collections.shuffle(shuffledByLetter,  rnd);
            for (List<String> list : shuffledByLetter) {
                Collections.shuffle(list, rnd);
                for (String word : list) {
                    if (word.equals(soln.words[word.charAt(0) - 'A'])) continue;
                    if (soln.canUse(word)) {
                        soln.use(word);
                        if (!theBitThatMatters.equals(Arrays.toString(soln.counts))) return soln;
                    }
                }

                // To avoid getting trapped in a local oscillation.
                int off = list.get(0).charAt(0) - 'A';
                if (soln.words[off] != null) {
                    soln.clear(off);
                    return soln;
                }
            }

            throw new RuntimeException("This really shouldn't be reachable");
        }

        @Override
        public String toString() {
            StringBuilder sb = new StringBuilder();
            for (String word : words) {
                if (word == null) continue;
                if (sb.length() > 0) sb.append(", ");
                sb.append(word);
            }

            return sb.toString();
        }

        private static int wordScore(String word) {
            int wordScore = 0;
            for (char ch : word.toCharArray()) {
                if (ch != '?') wordScore += (CHAR_VALUE.charAt(ch - 'A') - '0');
            }
            return wordScore * word.length();
        }

        public String toStringDetailed() {
            int score = 0;

            List<List<Integer>> lengths = new ArrayList<List<Integer>>();
            for (int i = 0; i < 26; i++) lengths.add(new ArrayList<Integer>());
            int unused = 100;

            StringBuilder surplusChars = new StringBuilder();
            int unusedBlanks = 2;

            StringBuilder sb = new StringBuilder();
            for (String word : words) {
                if (word == null) continue;
                for (char ch : word.toCharArray()) lengths.get(ch - 'A').add(word.length());
                unused -= word.length();
                sb.append(wordScore(word)).append("\t").append(word).append("\n");
            }

            for (int i = 0; i < 26; i++) {
                int limit = CHAR_FREQ.charAt(i) - '0';
                int off = 0;
                List<Integer> l = lengths.get(i);
                if (l.size() > limit) {
                    off = l.size() - limit;
                    unusedBlanks -= off;
                    Collections.sort(l);
                }
                while (l.size() < limit) {
                    surplusChars.append((char)('A' + i));
                    l.add(-unused);
                }
                for (int j = 0; j < off; j++) sb.append(-l.get(j)).append("\tfor blank used as ").append((char)('A' + i)).append("\n");
                for (; off < l.size(); off++) score += l.get(off) * (CHAR_VALUE.charAt(i) - '0');
            }

            while (unusedBlanks > 0) {
                surplusChars.append('?');
                unusedBlanks--;
            }
            sb.append(-wordScore(surplusChars.toString())).append("\t").append(surplusChars).append(" unused\n");

            sb.append("Total score: ").append(score());
            return sb.toString();
        }
    }
}

Python, score 2638 2675 2676 2689 2699 2717
Result:
OXYPHENBUTAZONE for 615
MICROEARTHQUAKE for 525
FLAVOURDYNAMICS for 435
ADJUSTABILITIES for 375
PREINTERVIEWING for 360
WATERFLOODINGS for 308
EAGLE?OOD? for 100
Left-over word: E
2717

Code:
import time
from multiprocessing import Pool

start_tiles = "AAAAAAAAABBCCDDDDEEEEEEEEEEEEFFGGGHHIIIIIIIIIJKLLLLMMNNNNNNOOOOOOOOPPQRRRRRRSSSSTTTTTTUUUUVVWWXYYZ??"
start_tiles = {l: start_tiles.count(l) for l in set(start_tiles)}
values = {"A": 1,"B": 3,"C": 3,"D": 2,"E": 1,"F": 4,"G": 2,"H": 4,"I": 1,"J": 8,"K": 5,"L": 1,"M": 3,"N": 1,"O": 1,"P": 3,"Q": 10,"R": 1,"S": 1,"T": 1,"U": 1,"V": 4,"W": 4,"X": 8,"Y": 4,"Z": 10,"?": 0}
with open("sowpods.txt") as f:
    full_dictionary = list(l.strip() for l in f if l.strip())

def num_wilds_needed(word, tiles):
    return sum(max(0, word.count(l) - tiles[l]) for l in word)

def word_is_possible(word, tiles):
    # never replace 1st letter with wild, for simplicity
    if tiles[word[0]] <= 0:
        return False

    return num_wilds_needed(word, tiles) <= tiles['?']

def word_score(word):
    return sum(values[c] for c in word) * len(word)

def final_score(words, tiles_left, print_leftover=False):
    left_over_word = ""
    for tile, counts in tiles_left.iteritems():
        left_over_word += tile * counts
    if print_leftover:
        print "Left-over word: %s" % (left_over_word,)
    return sum(word_score(word) for word in words) - word_score(left_over_word)

def filter_dictionary(dictionary, tiles_left, start_letters):
    return [word for word in dictionary
            if word[0] in start_letters and word_is_possible(word, tiles_left)]

def pick_word(next_word, start_letters, tiles_left, dictionary):
    if not word_is_possible(next_word, tiles_left):
        raise ValueError("Using word that is impossible: %s" % (next_word,))

    next_letters = set(start_letters)
    next_letters.remove(next_word[0])
    next_tiles = dict(tiles_left)
    for c in next_word:
        next_tiles[c] -= 1

    next_dictionary = filter_dictionary(dictionary, next_tiles, next_letters)

    return next_letters, next_tiles, next_dictionary

class FakeResult:
    def __init__(self, value):
        self.value = value
    def get(self, timeout=None):
        return self.value

class FakePool:
    def apply_async(self, f, args):
        res = f(*args)
        return FakeResult(res)

def proc_next_word(next_word,
                   start_letters, tiles_left, filtered_sorted_dictionary,
                   depth, picks, prefix):
    score = word_score(next_word)
    next_letters, next_tiles, next_dictionary = pick_word(
        next_word, start_letters, tiles_left, filtered_sorted_dictionary)

    if len(prefix) / 2 < 5:
        print "%sDepth %d: ?, %s for %d, %d possible words left" % (
            prefix, len(prefix) / 2, next_word, score, len(filtered_sorted_dictionary))

    next_words, next_score = search(FakePool(), next_letters, next_tiles, next_dictionary,
                                    depth-1, picks, prefix + "  ")

    if len(prefix) / 2 < 5:
        print "%sDepth %d: %d, %s for %d" % (
            prefix, len(prefix) / 2, score + next_score, next_word, score)

    return [next_word] + next_words, score + next_score

def wildify(word, tiles_left):
    # replace missing letters with wilds
    while True:
        for c in word:
            if tiles_left[c] < word.count(c):
                word = word[0] + word[1:].replace(c, '?',  word.count(c) - tiles_left[c])
                break
        else:
            break

    return word

def search(pool, start_letters, tiles_left, filtered_sorted_dictionary, depth, picks, prefix=""):
    if not filtered_sorted_dictionary:
        # no words left - penalize for tiles left
        return [], final_score([], tiles_left)

    if depth == 0:
        raise ValueError("Hit depth 0")

    if tiles_left['?'] > 0:
        # proc top few and re-calculate score based on wildcarding
        best_word_candidates = [wildify(w, tiles_left) for w in filtered_sorted_dictionary[:10000]]
        best_word_candidates.sort(key=word_score, reverse=True)
    else:
        # no wildification needed
        best_word_candidates = filtered_sorted_dictionary

    best_words = best_word_candidates[:picks]
    if depth == 1:
        # only look at 1 word since depth 0 will do nothing
        best_words = [best_words[0]]

    results = [pool.apply_async(proc_next_word, (next_word,
                                                 start_letters, tiles_left, filtered_sorted_dictionary,
                                                 depth, picks, prefix))
               for next_word in best_words]
    results = [result.get() for result in results]

    return max(results, key=lambda (words, result): result)

if __name__ == "__main__":
    start_letters = set("ABCDEFGHIJKLMNOPQRSTUVWXYZ")
    tiles_left = dict(start_tiles)
    print "Preparing word list..."
    dictionary = filter_dictionary(full_dictionary, tiles_left, start_letters)
    dictionary.sort(key=word_score, reverse=True)
    print "Starting search..."
    pool = Pool(8)
    words, _ = search(pool, start_letters, tiles_left, dictionary, 666, 5)

    for word in words:
        for c in word:
            if tiles_left[c] <= 0:
                raise ValueError("Invalid word list")
            tiles_left[c] -= 1

    print
    print "\n".join(("%s for %s" % (word, word_score(word)) for word in words))
    print final_score(words, tiles_left, True)

Explanation:
Depth-first search which searches the entire tree, picking between the top picks best words at each stage.
I sort the entire word list once by score at the beginning. After picking each word, for the next iteration I filter out all the words that are now no longer possible, preserving the order, so I don't have to sort the list at each step. To deal with wildcards, if there's a possibility that a wild card is needed, I pick the top 10000 candidates, replace missing letters with wildcards if needed, and re-sort based on the new (lower) scores.
This output is for picks=5 and took 8m01s to run on my 8-core machine.

Java 8, score 2641 2681
The program starts by taking the 40 best words. For each word, it finds the 40 best words to go along. Of the 1600 combinations, the program takes the best 40. For each combination, the 40 best words are found, and the cycle repeats.
When just a few tiles are left, the remaining letters are combined with the two blanks for the final word.
Update
I increased the threshold to the 50 best words. Also, each combination only adds words that are less than those already present. This prevents multiple permutations of the same group.
OXYPHENBUTAZONE: 615
MICROEARTHQUAKE: 525
INTERSUBJECTIVE: 435
DAFFADOWNDILLY: 406
PREINTERVIEWING: 360
AUTOALLOGAMIES: 238
GOODSIRES: 99
?A?: 3             (ZAX)
---
Total: 2681

The program:
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

public class Scrabble {

    static final int[] scores = new int[]{1, 3, 3, 2, 1, 4, 2, 4, 1, 8, 5, 1, 3, 1, 1, 3, 10, 1, 1, 1, 1, 4, 4, 8, 4, 10, 0};
    static final int[] freqs = new int[]{9, 2, 2, 4, 12, 2, 3, 2, 9, 1, 1, 4, 2, 6, 8, 2, 1, 6, 4, 6, 4, 2, 2, 1, 2, 1, 2};

    static final int MAX = 50;

    public static void main(String[] args) throws IOException {
        List<String> words = Files.readAllLines(new File("C:/Users/Ypnypn/scrabble.txt").toPath());
        words.sort((s, t) -> score(t) - score(s));
        words.removeIf(w -> !works(w));

        List<List<String>> last = words.stream().map(Arrays::asList).collect(Collectors.toList()),
                finalList = new ArrayList();

        for (int i = 0; i < 10; i++) {
            List<List<String>> next = new ArrayList();
            for (int j = 0; j < MAX && j < last.size(); j++) {
                List<String> group = last.get(j);
                Object[] thirds = words.stream().filter(word -> workTogether(group, word) && least(word, group)).toArray();
                for (int k = 0; k < MAX && k < thirds.length; k++) {
                    List<String> newList = new ArrayList(group);
                    newList.add((String) thirds[k]);
                    next.add(newList);
                }
            }
            last = next;
            last.sort((s, t) -> t.stream().mapToInt(Scrabble::score).sum()
                                - s.stream().mapToInt(Scrabble::score).sum());
            for (List<String> l : last) {
                if (l.stream().mapToInt(String::length).sum() > 90) {
                    finalList.add(l);
                }
            }
        }
        finalList.forEach(g -> {
            List<Integer> chars = new ArrayList();
            int[] counts = new int[26];
            g.forEach(str -> str.chars().forEach(c -> counts[c - 'A']++));
            for (int i = 0; i < 26; i++) {
                while (counts[i] < freqs[i]) {
                    chars.add('A' + i);
                    counts[i]++;
                }
            }
            String end = words.stream()
                    .filter(w -> w.length() == chars.size() + 2)
                    .filter(w -> g.stream().noneMatch(s -> s.charAt(0) == w.charAt(0)))
                    .filter(w -> {
                        List<Integer> copy = new ArrayList(chars);
                        int _1 = 0, _2 = 0;
                        for (char c : w.toCharArray()) {
                            if (copy.contains((int) c)) {
                                copy.remove((Integer) (int) c);
                            } else if (_1 == 0) {
                                _1 = c;
                            } else if (_2 == 0) {
                                _2 = c;
                            } else {
                                return false;
                            }
                        }
                        return true;
                    }).findAny().orElse("");
            if (end.equals("")) {
                return;
            }
            char[] arr = end.toCharArray();
            for (int i = 0; i < arr.length; i++) {
                if (chars.contains((int) arr[i])) {
                    chars.remove((Integer) (int) arr[i]);
                } else {
                    arr[i] = '?';
                }
            }
            g.add(new String(arr));
        });

        finalList.removeIf(g -> g.stream().mapToInt(String::length).sum() < 100);
        finalList.sort((s, t) -> t.stream().mapToInt(Scrabble::score).sum()
                                 - s.stream().mapToInt(Scrabble::score).sum());
        List<String> answer = finalList.get(0);
        for (String str : answer) {
            System.out.print(str + ": " + score(str));
            if (str.contains("?")) {
                String actual = words.stream().filter(s -> s.matches("^" + str.replace('?', '.') + "$")).findAny().get();
                System.out.print("             (" + actual + ")");
            }
            System.out.println();
        }
        System.out.println("---");
        System.out.println("Total: " + answer.stream().mapToInt(Scrabble::score).sum());
    }

    static boolean works(String str) {
        int[] counts = new int[26];
        for (char c : str.toCharArray()) {
            counts[c - 'A']++;
        }
        for (int i = 0; i < 26; i++) {
            if (counts[i] > freqs[i]) {
                return false;
            }
        }
        return true;
    }

    static boolean workTogether(List<String> strs, String str) {
        if (strs.stream().anyMatch(s -> s.charAt(0) == str.charAt(0))) {
            return false;
        }
        int[] counts = new int[26];
        strs.stream().forEach(s -> s.chars().forEach(c -> counts[c - 'A']++));
        str.chars().forEach(c -> counts[c - 'A']++);
        for (int i = 0; i < 26; i++) {
            if (counts[i] > freqs[i]) {
                return false;
            }
        }
        return true;
    }

    static boolean least(String str, List<String> strs) {
        int score = score(str);
        return strs.stream().allMatch(s -> score(s) >= score);
    }

    static int score(String word) {
        int score = 0;
        for (char c : word.toCharArray()) {
            if (c != '?') {
                score += scores[c - 'A'];
            }
        }
        return score * word.length();
    }
}

Perl, score: 2655 2630
#!perl -l
%p = qw{A 1 B 3 C 3 D 2 E 1 F 4 G 2 H 4 I 1 J 8 K 5 L 1 M 3 N 1 O 1 P 3 Q 10 R 1 S 1 T 1 U 1 V 4 W 4 X 8 Y 4 Z 10 x 0};
/[A-Z]+/,push @R,$& for <>;
@R = sort{length($b)<=>length($a)}@R;
for(@R) {push@W,$_;push@W,"$`x$'" while /./g;push@O,($_)x(1+length)}
$l = "AAAAAAAAABBCCDDDDEEEEEEEEEEEEFFGGGHHIIIIIIIIIJKLLLLMMNNNNNNOOOOOOOOPPQRRRRRRSSSSTTTTTTUUUUVVWWXYYZxx";
@S = map {$r='';for$x(A..Z,'x'){$r.="${x}{".(1*s/$x//g).",}"};"^$r\$"} map{"$_"}@W;
sub score{$r=0;$r+=$p{$_}for split'',$rr=pop;$r*length$rr}
@X = map{score$_}@W;
$f = 'x';
for(;;) {
$best = -1; $besti = 0;
for ($i=0;$i<@S;$i++) {
    next if $X[$i] < $best;
    if ($O[$i]!~/^[$f]/ && $l=~$S[$i]) {
    $best = $X[$i];
    $besti = $i;
    }
}
if($best < 0){
    $ls = score$l;
    print "left: $l (-$ls)";
    $tot -= $ls;
    print "total: $tot";
    exit;
}
$l=~s/$_// for $W[$besti]=~/./g;
$O[$besti]=~/./; $f .= $&;
print "$W[$besti]/$O[$besti] ($X[$besti])";
$tot += $X[$besti];
}

Use:
$ perl ./scrab.pl <~/sowpods.txt
OXYPHENBUTAZONE/OXYPHENBUTAZONE (615)
MICROEARTHQUAKE/MICROEARTHQUAKE (525)
NONOBJECTIVISMS/NONOBJECTIVISMS (465)
DAFFADOWNDILLY/DAFFADOWNDILLY (406)
PREINTERVIEWIxG/PREINTERVIEWING (345)
LITURGIOLOGxSTS/LITURGIOLOGISTS (240)
URDEE/URDEE (30)
EE/EE (4)
AA/AA (4)
left: AA (-4)
total: 2630

Use of blanks actually does not give that much while significantly slows down the execution:
$ perl ./scrab.pl <~/sowpods.txt
OXYPHENBUTAZONE/OXYPHENBUTAZONE (615)
MICROEARTHQUAKE/MICROEARTHQUAKE (525)
NONOBJECTIVISMS/NONOBJECTIVISMS (465)
DAFFADOWNDILLY/DAFFADOWNDILLY (406)
PREINTERVIEWED/PREINTERVIEWED (322)
LITURGIOLOGISTS/LITURGIOLOGISTS (255)
RUGAE/RUGAE (30)
EE/EE (4)
AA/AA (4)
left: Axx (-3)
total: 2623

After adding some heuristics:
$ time perl ./scrab.pl <~/sowpods.txt
OXYPHENBUTAZONE/OXYPHENBUTAZONE (615)
MICROEARTHQUAKE/MICROEARTHQUAKE (525)
NONOBJECTIVISMS/NONOBJECTIVISMS (465)
PREFIGURATIVELY/PREFIGURATIVELY (405)
DOWNREGULATIONS/DOWNREGULATIONS (300)
FORGEAxILITIES/FORGEABILITIES (238)
ADWAxDED/ADWARDED (104)
EA/EA (4)
left: L (-1)
total: 2655

real    3m58.517s
user    3m57.832s
sys 0m0.512s

Python 3, score 2735
(The optimal score of 2765, "6 words of 15 letters and one 10-letter word consisting of 8 letters of value 1 and two blanks" has been achieved by nutki.)
I used a greedy approach similar to others':
I start with one-element lists containing the top scoring words containing Q's.
At every step for every list element I create k = 800 new lists with the best legal words for the list. From the aggregated list of lists I keep the k top scoring lists and repeat the process 10 times.
Note that you can get the top k elements of an n-long list in O(n + k*log n) which is O(n) if k<<n as in our case (k = 800, n ~= 250000) with a heap queue.  I guess this method isn't used in other submission s hence the smaller k values.
I use wildcards along the way if needed for the words.
Runtime is a couple minutes for k = 800. Greater values and other optimizations haven't yielded better results yet.
Result:
DEMISEMIQUAVERS for 480
OXYPHENBUTAZONE for 615
ACKNOWLEDGEABLY for 465
FLASHFORWARDING for 435
INTERJACULATING for 375
COOPERATIVITIES for 330
METEOROID for 108
? is C for -45
? is M for -27
Left U for -1
Total score of 2735

I experimented with the Descartes product of the best words containing Q,J and X as these letter barely share words. My best score with this startegy was 2723 (DEMISEMIQUAVERS OXYPHENBUTAZONE INTERSUBJECTIVE FLASHFORWARDING KNOWLEDGABILITY RADIOPROTECTION ANALOGUE EA).
The unnecessary complicated spaghetti-code (with traces of experimentation with other methods):
import sys,heapq as hq

def score(s):
    r=0
    for c in s:
        r+=ord('1332142418513113:11114484:0'[ord(c)-65])-48
    return r*len(s)

def score_wl(rwl):
    ac=a[:]
    ssd=0
    for rwle in rwl:
        ac,sd=decr(ac,rwle)
        ssd+=sd
    return sum([score(rw) for rw in rwl])-ssd

def decr(av,nw):
    nav=av[:]
    scd=0
    for c in nw:
        if nav[ord(c)-65]>0:
            nav[ord(c)-65]-=1
        else:
            nav[ord('[')-65]-=1
            scd+=(ord('1332142418513113:11114484:'[ord(c)-65])-48)*len(nw)
    return (nav,scd)

def bestwordlist(w,ac,sw,count):
    stl=[swe[0] for swe in sw]
    sl=[]
    for we in w:
        if we[0] not in stl:
            acn,sd=decr(ac,we)
            if min(acn)>=0:
                sl+=[(we,score(we)-sd)]
    mw=hq.nlargest(count,sl,key=lambda p:p[1])
    res=[mwe[0] for mwe in mw]
    return res

def bestword(w,ac,sw):
    ms=0
    mw=''
    stl=[swe[0] for swe in sw]
    for we in w:
        if we[0] not in stl:
            acn,sd=decr(ac,we)
            if min(acn)>=0 and score(we)-sd>ms:
                ms=score(we)-sd
                mw=we
    return mw

def search(t,lev,av,sw):
    if lev>=len(t) and min(av)>=0:
        return [sw]
    if min(av)<0:
        return []
    r=[]
    stl=[swe[0] for swe in sw]
    if av[ord(tl[lev])-65]>0:
        for i in range(1,maxch):
            nw=t[lev][-i][0]
            if nw[0] not in stl:
                nav=decr(av,nw)[0]
                swn=sw[:]+[nw]
                r+=search(t,lev+1,nav,swn)
    else:
        r+=[sw]
    if len(r)<10000:
        return r
    else:
        return hq.nlargest(10000,r,key=score_wl)

args=sys.argv
maxch=300#int(args[1])
maxch2=800#int(args[2])

w=[]
with open('scr_words.txt','r') as f:
    for l in f:
        w+=[l[:-1]]

a=[ord(c)-48  for c in '9224<2329114268216464221212']
                       #ABCDEFGHIJKLMNOPQRSTUVWXYZ?

t=[]
tl='Q'
for c in tl:
    tp=[]
    wl=[(x,score_wl([x])) for x in w if c in x]
    wl=sorted(wl,key=lambda p:p[1])
    t+=[wl]

r=search(t,0,a,[])

rt=sorted(r,key=score_wl)[-maxch2:]

ms=0
res='-'

for i in range(10-len(tl)):
    rtn=[]
    for sw in rt:

        ac=a[:]
        for swe in sw:
            ac,sd=decr(ac,swe)

        bwl=bestwordlist(w,ac,sw,maxch2)

        if not bwl:
            rtn+=[sw]
        for bwle in bwl:
            rtn+=[sw+[bwle]]

    rt=sorted(rtn,key=score_wl)[-maxch2:]
    print(rt[-1],score_wl(rt[-1]),'- left')
    sys.stdout.flush()

ms=-1000000
for sw in rt:
    ssd=0
    ac=a[:]
    for swe in sw:
        ac,sd=decr(ac,swe)
        ssd+=sd
    sc=sum([score(swe) for swe in sw])-ssd
    left=''.join([chr(i+65)*v for i,v in enumerate(ac)])
    sc-=score(left)
    if sc>ms:
        ms=sc
        res=(sw,left)

fsw,left=res
print('\n\nres =',ms,' '.join(fsw),'left',left)
    v

all_licenses: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/3.0/


text:
Simplest Tiling of the Floor
You should write a program or function which receives a string describing the floor as input and outputs or returns the area of the simplest meta-tiling which could create the given pattern of the floor.
The floor is a part of a square grid. Every square tile is colored either azure or black (represented by a and b in the input).
An example floor:
  aaaa
ababab
aaaaa

A meta-tiling

is built from an N by M rectangular meta-tile of azure and black squares
the used meta-tiles are identical up to translation (you cannot rotate or mirror them)
if the sides of two meta-tiles are connected they should connect along their whole length (i.e. meta-tiles tile the space in a grid-like fashion)

An example meta-tile:
ba
aa

and the meta-tiling created by it:
       .
       .
       .
    babababa
    aaaaaaaa
... babababa ...
    aaaaaaaa
    babababa
    aaaaaaaa
       .
       .
       .

This meta-tiling creates the upper shown floor as the left letters show:
       .
       .
       .
    ********
    ***aaaa*
... *ababab* ...
    *aaaaa**
    ********
    ********
       .
       .
       .

A meta-tiling is simpler than another if the area of its meta-tile is smaller. Our example has an area of 2*2 = 4 which is the smallest possible for the example floor. So the output should be 4 for the example.
Input

A string consisting of the characters a b space and newline containing at least one a or b.
The letters (ab) form one 4-connected (side-by-side connected) shape.
There will be no unnecessary spaces at the front of the rows i.e. there will be at least one row starting with a or b.
You can choose of two input format:

No unnecessary whitespace at the end of rows (as seen in the examples).
Spaces on the right side of the rows to make all rows the same length as the longest row.

Trailing newline is optional.

Output

A single integer, the area of the smallest possible meta-tile whose tiling contains the input floor.

Examples
Examples are delimited by dashes. The three parts of an example are input, output and one of the possible smallest meta-tiles.
a

1

a
-----------------
 aaaa
aaa
a

1

a
-----------------
aabaab
abaa
aaba

6

aab
aba
-----------------
aabaab
a  a a
aabab

18

aabaab
aaaaaa
aababa
-----------------
ba
aaab

8

baaa
aaab
-----------------
 aaaa
ababb
aaaa

10

aaaaa
ababb
-----------------
 a aa
ab ba
 aba

6

aa
ab
ba
-----------------
 aaaa
abab
aaaa

4

aa
ab
-----------------
ba
 ba
  b

4

ba
ab
-----------------
baa
aba
aab

9

baa
aba
aab
-----------------
 aaaa
aabaa
aaaa

6

aaa
aab

This is code golf so the shortest entry wins.

@Ypnypn Every corner has to touch 3 other corners (except the meta-tiles on the edge of the tiling). I stated it as "if the sides of two meta-tiles are connected they should connect along their whole length". So your given example is illegal.

C - 208 bytes
w,q,n,m,r,g,u;t(char*f){for(w=0;f[w++]-10;);for(q=1;;q++)for(n=1;m=q/n,n<=q;++n)if(n*m==q){char t[q];bzero(t,q);r=q;for(g=0;f[g];++g){u=g/w%m*n+g%w%n;r=t[u]+f[g]-195?r:0;if(f[g]&64)t[u]=f[g];}if(r)return r;}}

Equivalent code before golfing:
#include <stdio.h>
#include <strings.h>

int t(char* f) {
    int w = 0;
    for ( ; f[w++] - 10; );

    for (int q = 1; ; q++) {
        char t[q];
        for (int n = 1; n <= q; ++n) {
            int m = q / n;
            if (n * m == q) {
                bzero(t, q);
                int r = q;
                for (int g = 0; f[g]; ++g) {
                    int u = g / w % m * n + g % w % n;
                    if (t[u] + f[g] == 195) {
                        r = 0;
                    }
                    if (f[g] & 64) {
                        t[u] = f[g];
                    }
                }
                if (r) {
                    return r;
                }
            }
        }
    }
}

The algorithm is fairly brute force, so it should be reasonably obvious how it works based on the code. Here are a few comments anyway:

Input is expected to have the form with trailing spaces so that all lines have the same length.
First loop finds the width by looking for first newline character.
Outer loop is over candidate meta-tile sizes q. Exits with a return when a meta-tile can cover the floor. Note that the loop does not need another exit condition since there is always a solution (worst case is size of input).
First nested loop and following if enumerates valid meta-tile width/height combinations for size q.
A character array matching the candidate meta-tile size is zero-initialized.
Inner loop iterates over all tiles in the floor.
u is the index in the meta-tile that corresponds to the floor tile.
If both floor tile and meta-tile tile are a or b and different (sum of a = 97 and b = 98 is 195), there is a mismatch, and the meta-tile size with the attempted dimensions will not work.
Otherwise, if the floor tile is a or b, the tile color is copied to the candidate meta-tile.
Returns size of meta-tile when successful match was made, i.e. if the attempted match was not marked as failed.

Test code used:
#include <stdio.h>

extern int t(char* s);

int main()
{
    printf("%d\n", t(
        "a\n"
    ));
    printf("%d\n", t(
        " aaaa\n"
        "aaa  \n"
        "a    \n"
    ));
    printf("%d\n", t(
        "aabaab\n"
        "abaa  \n"
        "aaba  \n"
    ));
    printf("%d\n", t(
        "aabaab\n"
        "a  a a\n"
        "aabab \n"
    ));
    printf("%d\n", t(
        "ba  \n"
        "aaab\n"
    ));
    printf("%d\n", t(
        " aaaa\n"
        "ababb\n"
        "aaaa \n"
    ));
    printf("%d\n", t(
        " a aa\n"
        "ab ba\n"
        " aba \n"
    ));
    printf("%d\n", t(
        " aaaa\n"
        "abab \n"
        "aaaa \n"
    ));
    printf("%d\n", t(
        "ba \n"
        " ba\n"
        "  b\n"
    ));
    printf("%d\n", t(
        "baa\n"
        "aba\n"
        "aab\n"
    ));
    printf("%d\n", t(
        " aaaa\n"
        "aabaa\n"
        "aaaa \n"
    ));
    return 0;
}

Output:
1
1
6
18
8
10
6
4
4
9
6

APL(Dyalog Unicode), 53 37 36 bytes SBCS
{⌊/×/¨⍸(~6∊' a'∧/⍤⍳⍵⊢⌸⍥,⍨|)⍤0 2⍨⍳⍴⍵}

Try it on APLgolf!
Instead of partitioning, this one groups the characters in the matrix by their 2D indices modulo current size. I came up with it independently, but apparently it's the same as Zgarb's idea. But there's a funky part in this solution: in order to test if a group contains both a and b, it maps space/a/b into 1, 2, 3 respectively via find-index function, and calculates their LCM to see if it is 6.

APL (Dyalog Unicode), 53 bytes
{⌊/×/¨⍸{∧/,⍲/¨'ab'∘∊¨⊃{⍉,⌿↑⍺⊂⍵}/(⊂,⍨⍴⍴¨⍺↑¨≡)⍵}∘⍵¨⍳⍴⍵}

Try it online!
A function that takes a character matrix as the argument. Basically, tries all possible tile sizes, testing if partitioning by that size would give at most one of ab on every cell.
Illustration
Example input:
 a aa
ab ba
 aba
Example tile size: 2 rows, 2 columns
Partition:
+--+--+-+
| a| a|a|
|ab| b|a|
+--+--+-+
| a|ba| |
+--+--+-+
Cells collected into a tile:
+------+------+
|  a b |aa aa |
+------+------+
|a a   |bb    |
+------+------+
Since top left cell has both a and b, this tile size is invalid.

How the code works
{⌊/×/¨⍸{∧/,⍲/¨'ab'∘∊¨⊃{⍉,⌿↑⍺⊂⍵}/(⊂,⍨⍴⍴¨⍺↑¨≡)⍵}∘⍵¨⍳⍴⍵}
             ⍝ ⍵ ← Char matrix
        ⍳⍴⍵  ⍝ Generate possible tile sizes as a matrix of length-2 vectors
{...}∘⍵¨     ⍝ Test if each tile size is valid...
             ⍝   ⍵ ← Input char matrix, ⍺ ← tile size
(⊂,⍨⍴⍴¨⍺↑¨≡)⍵  ⍝ Create partition vectors and join with ⍵ for RTL reduction
(         ≡)⍵  ⍝ Depth of ⍵, which always gives 1 for valid input
       ⍺↑¨     ⍝ Overtake 1 to the length of each of ⍺, e.g. (1 0)(1 0 0)
    ⍴⍴¨        ⍝ Cycle each to the length of the dimensions of ⍵,
               ⍝ e.g. (1 0 1 0 1)(1 0 0 1 0)
 ⊂,⍨           ⍝ Append the enclosed ⍵
⊃{⍉,⌿↑⍺⊂⍵}/  ⍝ Partition and collect all cells at the same position in the tile
 {       }/  ⍝ Reduce by...
      ⍺⊂⍵    ⍝ Partition ⍵ into consecutive columns at 1s of ⍺
     ↑       ⍝ Mix so that short partition is padded with spaces
   ,⌿        ⍝ Collect the cells at the same position
  ⍉          ⍝ Transpose to do the same for rows
⊃            ⍝ Disclose one level of nesting (which is a side effect of /)
∧/,⍲/¨'ab'∘∊¨  ⍝ Test if no tile position contains both a and b
      'ab'∘∊¨  ⍝ For each tile position, evaluate (has a)(has b)
   ⍲/¨         ⍝ Reduce each by NAND; 1 if the tile position has at most one of ab
∧/,            ⍝ Test if it is true for all positions
⌊/×/¨⍸  ⍝ Extract the answer (the smallest area)
     ⍸  ⍝ 1-based coordinates of ones; the tile sizes which passed the test
⌊/×/¨   ⍝ Minimum of the areas

Husk, 30 bytes
ḟ(SδV(ΛË←k→f←δṁz,¶⁰¤Ṫeo¢ḣ)↔Ḋ)1

Try it online!
Explanation
I loop through all nonnegative integers until I find one that, when split into two factors in some way, gives a horizontal and vertical period for the input patch.
The period is checked by grouping the 2D indices of non-space characters by their values modulo the two numbers, and checking that each group contains equal characters.
ḟ(…)1   Starting from 1, find a number that satisfies (…).

SδV(…)↔Ḋ   We're looking at a number, say n=6.
       Ḋ   Divisors: d = [1,2,3,6]
S     ↔    Reverse and apply to both:
 δV(…)     does any pair from d and its reverse satisfy (…)?
           For n=6, the pairs are (1,6), (2,3), (3,2), and (6,1).

ΛË←k→f←δṁz,¶⁰¤Ṫeo¢ḣ   Check if (a,b) is a valid metatile.
             ¤        For both a and b:
                  ḣ     take range from 1 to it
                o¢      and cycle it infinitely.
              Ṫ       Combine these by taking outer product by
               e      pairing.
                      For (a,b)=(2,3), this gives the infinite 2D array
                      A=[[[1,1],[1,2],[1,3],[1,1],..],
                         [[2,1],[2,2],[2,3],[2,1],..],
                         [[1,1],[1,2],[1,3],[1,1],..],
                         ..]
           ¶⁰         The input, split at newlines.
       δṁ             For each row of it and A:
         z,             zip them (discarding overflowing rows and pairs of A)
       δṁ               and concatenate the results.
                      Now we have a list of pairs like ('a',[2,3]) that contain
                      a character from the input and its coordinates mod (a,b).
     f←               Keep those whose left part is truthy, i.e. not a space.
   k→                 Classify (into separate lists) by right part.
Λ                     Does every class
 Ë←                   have all equal left parts?

Pip -r, 52 bytes
MN:$*_M{$&{$*$Q*$.aDCs}M_UWa@1MMyUW@a}FI\,#gCP\,#@Yg

Takes input from lines of stdin, with trailing spaces as needed. Try it online!
Approach taken from Bubbler's APL answer: We try all possible meta-tile dimensions, filtering for the ones that have a unique non-space character at each position. UW (unweave) is very useful for grouping the input grid by tile positions. We then multiply each successful pair of dimensions to get the area of the tile, and take the minimum.
Leave a comment if you'd like a more detailed explanation.

Brachylog, 44 bytes
∧ℕf⟨≡z↔⟩∋[X,Y]×.&ṇġ↙Xz₁ġᵐ²↙Yz₁ᵐ²zᵐ{c;Ṣx=}ᵐ²∧

Try it online!
A port of Zgarb's Husk answer. Brachylog doesn't have infinite lists or cyclic indexing, so instead I'm using the "groups" predicate ġ ([1,2,3,4,5]ġ₂ -> [[1,2],[3,4],[5]]) and then zip z ([[1,2],[3,4],[5]]z₁ -> [[1,3,5],[2,4]]) to get lists of the characters at tile-equivalent positions.

all_licenses: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/4.0/


text:
Order and Chaos and Codegolf
Order and Chaos is a variant of Tic-Tac-Toe played on a 6x6 board. What makes the game unique, however, is that both players can place either an X or an O! Each turn (starting with Order), a player places an X or O in any unoccupied square.
Winning is simple. Order wins if there are 5 Xs or Os (vertically, horizontally, or diagonally) in a row on the board. Chaos wins if the board is filled and there are no strings of 5 Xs or Os on the board. Your job? Well, since this is Programming Puzzles and Code Golf, you're going to program the game, and golf it.
The Rules

You must accept input as x y t, where x and y are coordinates, and t is the tile type (X or O). Coordinates start with 0 0 in the upper-left corner and increase up to 5 5 (the lower-right corner).
You must accept q to quit, and print INVALID if the user enters invalid coordinates, tiles, any input not in the form of x y t, or tries to place a tile where there already is one. (The only exception is q, as this quits the program.)
If Order wins, you will output P1 WINS. If Chaos wins, you will output P2 WINS.
Order must go first.
A blank space is represented by ..
Tiles are X and O (uppercase). You do not have to accept lowercase, but uppercase is required.
Your board must only consist of .XO.
You're actually simulating both players playing the game, not being given a board and checking who wins. It accepts a move as input, then prints the board, accepts another move, and so on, until one player wins.

The starting board looks like this:
......
......
......
......
......
......

And after the first player (Order) inputs 1 2 X, it should look like this:
......
......
.X....
......
......
......

Likewise, when the next player (Chaos) inputs 3 3 O, it will look like this:
......
......
.X....
...O..
......
......

And this continues until one player wins.
As always, Standard loopholes which take the fun out of everything are forbidden.
The winner is the one with the shortest code on June 15, 00:00 UTC (about one month from when this challenge was posted.)

What if a player types in a position that is already taken?

@Loovjo It returns INVALID. I've edited that in now, thanks.

Should the game exit once 5 tiles are in a row are detected?

Maybe I overlooked it but does it have to print the board to the screen or just check the state of the board and output which player wins?

@Andrew I actually meant to simulate the game. You accept each player's input, one turn at a time, and then check if a player has won each turn. Is the description unclear?

@KyleKanos Yes. Once 5 tiles are in a row, it quits and prints ORDER WINS.

@ASCIIThenANSI ORDER WINS or P1 WINS?

@xebtl Sorry, messed that up. It prints P1 WINS if there are 5 tiles in a row, and P2 WINS if the board is full with no chains of 5 tiles in a row.

Yes the description is unclear. The board have to be printed at each turn or not?

@edc65 Yes, it does. I'll make sure it's clearer.

PHP, 316
Here is my submission. It has to be executed by php in the command line.
Note that this code produces notices because of some shortcuts I made. Let me know if this is ok. I can fix it by adding a few more characters. I checked this page and the top answer says to assume that error reporting is turned off if there is no mention about it.
<?for(;$i++<6;)$b.='......|';while(($a=trim(fgets(STDIN)))!='q'){preg_match('/^([0-5]) ([0-5]) ([XO])$/',$a,$d)&($b[$c=$d[2]*7+$d[1]]=='.')?$b[$c]=$d[3]:print"INVALID\n";echo str_replace("|","\n",$b); foreach([0,5,6,7]as$e)preg_match('/(X|O)(.{'.$e.'}\1){4}/',$b)-1?:die("P1 Wins");strstr($b,'.')?'':die("P2 Wins");}

And here is the un-golfed version of the code:
<?php
error_reporting(E_ALL & ~E_NOTICE);

for(;$i++<6;)$b.='......|';
while(($a=trim(fgets(STDIN)))!='q'){

    #Validate and assign
    preg_match('/^([0-5]) ([0-5]) ([XO])$/',$a,$d)&($b[$c=$d[2]*7+$d[1]]=='.')?$b[$c]=$d[3]:print"INVALID\n";

    #Output
    echo str_replace("|","\n",$b);

    #Check if Order wins
    foreach([0,5,6,7]as$e) {
        preg_match('/(X|O)(.{'.$e.'}\1){4}/',$b)-1?:die("P1 Wins");
    }

    #Check if Chaos wins
    strstr($b,'.')?'':die("P2 Wins");
}

Yes, notices are OK.

JavaScript, 360
Edit Modified interactive game, should run even in MSIE
As requested, text based game, input via popup, output in console (so to have a monospaced font).
Quit game with 'q' or clicking 'cancel' at prompt.
Not using ES5 features, it should run on any moder browser (where you can have a JS console panel)

b='\n......'.repeat(6).split('');
for(h=t=0;!h&t<36;)
{
  i=prompt();
  if(i=='q')i=null;
  i=i.match(/([0-5]) ([0-5]) ([XO])/);
  m='INVALID';
  if(b[p=i?i[2]*7-~i[1]:0]=='.')
  {
    ++t;
    b[p]=i[3];
    m=b.join('');
    for(x=z='',c=0;c++<6;)
      for(x+='_',z+='_',r=0;r<6;r++)
        x+=b[c+r*7],z+=b[c<4?c-1+r*8:c+1+r*6];
    h=(/X{5}|O{5}/.test(b.join('')+x+z))
  }
  console.log(m);
}
console.log("P"+(2-h)+" WINS")

Now, some more fun Interactive and graphic version, run snippet to play.

function start() {
  b=Array(7).join('\n......').split('');
  t=0;
  $('#O').text('');
  $('table')[0].className='';
  show();
  $('th').eq(1).html('Left-click: O
Right-click: X');
  $('#B')
  .off('mouseup')
  .on('mouseup','td.F',function(ev){
    var x,y, p=~~this.id.slice(1)
    x=p%7-1
    y=p/7|0
    b[p]=ev.which > 1 ?'X':'O';
    ++t
    for(x=z='',c=0;c++<6;)
      for(x+='_',z+='_',r=0;r<6;r++)
        x+=b[c+r*7],z+=b[c<4?c-1+r*8:c+1+r*6];
    show()
    if (/X{5}|O{5}/.test(b.join('')+x+z))
      end(1)
    else if(t==6*6)
      end(2)
    return false
  })
}

function end(w) {
  var n=['Order','Chaos'][w-1]
  $('th').eq(0).text('P'+w+' '+n+' Wins')
  $('th').eq(1).text('Click to play again')

  $('table')[0].className=$('tr')[0].className =n[0];
  $('#B').off('mouseup').on('mouseup', start)
}
function show() {
  var w,p
  p=t&1
  $('tr')[0].className=$('#B')[0].className='OC'[p];
  w=b.map(function(c,i){
    return c>' '?''+c+'	':'

'
  }).join('');
  $('th').eq(0).text('Playing: '+['Order','Chaos'][p]);
  $('#B').html('
' + w +'
');
}

start()
th {
  font-size: 12px;
}
.C th { color: #807; }
.O th { color: #047; }
.C td.F:hover { background: #f0e; }
.O td.F:hover { background: #0fe; }
table.C td { background: #f0e; }
table.O td { background: #0fe; }

td {
  font-family: monospace;
  font-size: 12px;
  width: 1.2em;
  height: 1em;
  text-align: center;
}

Nice clickable version!  (Minor suggestion: you could use right/left click instead of the radio buttons.)

@xebtl I'll give it a try

Octave, 453
format plus 'XO.'
disp(F=zeros(6))
r=@()fread(0,1);R=@()r()-47;q=@(m)printf(m)&&quit;e=@()q("INVALID");l=@(n)n<1||n>6&&e();s=@()r()==32||e();w="P1 WINS";f=@(v)abs(sum(v))==22.5&&q(w);g=@(m)any(abs(sum(m))==22.5)&&q(w);d=@diag;while 1
i=R();i==66&&quit;l(i);s();l(j=R());s();F(j,i)&&e();abs(v=R()-36.5)==4.5||e();F(j,i)=v;disp(F)
r();f(d(F,-1));f(d(F,0)(2:6));f(d(F,0)(1:5));f(d(F,1));g(F(1:5,:));g(F(2:6,:));g(F(:,1:5)');g(F(:,2:6)');F&&q("P2 WINS");end

The implementation is quite straightforward, the only real “trick” to use format plus to take care of printing.
Here is a commented version:
format plus 'XO.'               # this is where the magic happens

## initialize and print empty board
disp(F=zeros(6))

## shortcuts
r=@()fread(0,1);
R=@()r()-47;
q=@(m)printf(m)&&quit;
e=@()q("INVALID");
l=@(n)n<1||n>6&&e();
s=@()r()==32||e();
w="P1 WINS";
f=@(v)abs(sum(v))==22.5&&q(w);
g=@(m)any(abs(sum(m))==22.5)&&q(w);
d=@diag;

while 1
  i=R();                        # read index 1
  i==66&&quit;                  # ‘q’?
  l(i);                         # check bounds
  s();                          # read and check space
  l(j=R());                     # read and check index 2
  s();                          # read and check space
  F(j,i)&&e();                  # square already filled?
  abs(v=R()-36.5)==4.5||e();    # valid mark?
  F(j,i)=v;                     # assign …
  disp(F)                       # and print board
  r();                          # read off newline

  ## check diagonals
  f(d(F,-1));
  f(d(F,0)(2:6));
  f(d(F,0)(1:5));
  f(d(F,1));

  ## check rows
  g(F(1:5,:));
  g(F(2:6,:));

  ## check columns
  g(F(:,1:5)');
  g(F(:,2:6)');

  ## check chaos
  F&&q("P2 WINS");
end

Because of the requirement to check input syntax and validity, the code uses fread() to read one character at a time.
I took care to output the board and messages in a tidy manner.  If some extra output is acceptable, I could shave off a couple of bytes.  For example, using automatic printing (no disp(F)), the board would be shown as
F =

......
......
......
......
......
......

Also, I interpreted that each move is given on a separate line.

Sample interaction (the -q switch is just to suppress Octave's header):
$ octave -q order_chaos.m
......
......
......
......
......
......
3 3 X
......
......
......
...X..
......
......
2 3 O
......
......
......
..OX..
......
......
3 3 O
INVALID

The invalid move caused the program to exit (not sure if that was intended).

Just to make sure (because there was some confusion earlier), this takes input from both players, and actually simulates the game, rather than just checking if a given board wins?

@ASCIIThenANSI Just so. It expects each move of the form x y t on a separate line (and no other input).

And it prints the board after every input?

@ASCIIThenANSI Yes, see edited answer.

Java, 565 chars D:
public class M{public static void main(String[]r){int[]p=new int[36];int u=0;for(;;){String l=new java.util.Scanner(System.in).nextLine();if(l == "q")break;int a=l.charAt(0)-'0'+(l.charAt(2)-'0')*6,i=p[a]==0?1:0;if(i>0)p[a]=l.charAt(4);u+=i;r(i==0?"INVALID\n":"");if(u==36){r("P2 WINS");break;}for(int x=0;x<6;x++)for(int y=0;y<6;y++)for(int d=0;d<3;d++)try{int e=1,c=p[x+y*6],z=x,h=y;if(c=='X'||c=='Y'){for(;e<6;e++){if(d%2==0)z++;if(d>0)h++;if(p[z+h*6]!=c)break;}if(e==5){r("P1 WINS");return;}}}catch(Exception e){}}}static void r(Object o){System.out.print(o);}}

This is probably the longest code-golf ever. I'm really not good at this.