I believe the only users that should be impacted would be users with the Customize Application permission who continue to make modifications to your org's configuration during the deployment validation process (such as modifying a validation rule or updating a sharing setting). They should get a message that the org is locked and be unable to save their changes, which is more of a disruption in their access than anything that could impact the results of the validation. However, it is possible that a user could be in the middle of some long-running process (such as running test cases or updating sharing settings) that could prevent the validation from even starting in the first place.
Also, if your test cases rely on certain data being present and in a particular configuration (rather than mocking up the data as part of the test case, which is a best practice), allowing users to make changes to data in the org during the validation window could potentially impact the success of your test cases. Of course, this is easily preventable by writing test cases that create their own data or ensuring that they utilize the @IsTest(SeeAllData=false)
annotation introduced in API version 24.0.
Other than that, your end-users really should not be impacted by a validation-only deployment, as all changes introduced are never actually committed and will be rolled back following the completion of all tests. In my experience, locking out all users should only be necessary during the actual deployment window (especially when manual configuration changes are necessary in addition to the automated deployment and it would be undesirable/dangerous for a user to be accessing the system prior to the completion of the manual changes).
The apex version available changes with each release. So, with Winter '14 the, apex version 29 becomes available.
Unless you change it explicitly, classes retain the version that they have when they are created. So when you are looking at the other classes in production and seeing numbers less than 27, that probably was the latest version when those classes were initially developed.
Why you might be happy leaving a class on an older version of Apex
The benefit of this is that the language behaves the way that it did when the class was written and you don't need to do extensive regression testing.
Why you might want to set a class to a newer version of Apex
If you are working with a class developed against an older version of Apex, you may need to increase the version number in order to take advantage of features exposed in later versions of the API.
Why you might have API version trouble when deploying
By default new classes and triggers are created with the latest version of API. If you are working in a Sandbox this may be one version ahead of the Production org, depending on the release window. For example my sandbox is now version 29 (Winter '14) but Production is version 28 (Summer '13). In order to deploy a new class now I would need to save it with the lower version, version 28.
Also if you are deploying through ANT, Salesforce Migration Tool etc. then you need to ensure that the API version specified in your package.xml is at least as high as the the API version of what you are deploying.
How to set the API version
The api version is changed manually, either through the UI
or if you are deploying through ANT or Salesforce IDE, by amending the metadata file which is called theapexclassname-meta.xml
<?xml version="1.0" encoding="UTF-8"?>
<ApexClass xmlns="http://soap.sforce.com/2006/04/metadata">
<apiVersion>25.0</apiVersion>
<status>Active</status>
</ApexClass>
Best Answer
Sounds like your sandbox is on Summer '15 (Api v34) while your production instance is on Spring '15 (Api v33).
In your sandbox, go through all the components and (where possible) set their API version back to 33. This should allow the components to be accepted by the production instance.
Worst case scenario, wait until next week as your production instance will be upgraded to Summer '15 this weekend.