The only sure way to release the memory that I can think of is to swap with a temporary vector:
vector<array<double,1000>> S1(1000);
...
vector<array<double,1000>>().swap(S1);
Although this might look strange at first, it is a known, widely used idiom.
In C++11, moving from the original vector might be an option, although it is not guaranteed to clear the memory or even clear the vector (I cannot think of a reason why an implementation wouldn't do that though):
{
vector<array<double,1000>> tmp(std::move(S1));
} // tmp dies on exiting scope, memory is cleared
Altenratively, a call to std::vector::shrink_to_fit
could result in memory de-allocation, but there are no guarantees:
S1.clear();
S1.shrink_to_fit();