|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#ifndef moses_TargetPhraseCollectionCache_h |
|
|
#define moses_TargetPhraseCollectionCache_h |
|
|
|
|
|
#include <map> |
|
|
#include <set> |
|
|
#include <vector> |
|
|
|
|
|
#include <boost/thread/tss.hpp> |
|
|
#include <boost/shared_ptr.hpp> |
|
|
|
|
|
#include "moses/Phrase.h" |
|
|
#include "moses/TargetPhraseCollection.h" |
|
|
|
|
|
namespace Moses |
|
|
{ |
|
|
|
|
|
|
|
|
typedef std::vector<TargetPhrase> TargetPhraseVector; |
|
|
typedef boost::shared_ptr<TargetPhraseVector> TargetPhraseVectorPtr; |
|
|
|
|
|
|
|
|
class TargetPhraseCollectionCache |
|
|
{ |
|
|
private: |
|
|
size_t m_max; |
|
|
float m_tolerance; |
|
|
|
|
|
struct LastUsed { |
|
|
clock_t m_clock; |
|
|
TargetPhraseVectorPtr m_tpv; |
|
|
size_t m_bitsLeft; |
|
|
|
|
|
LastUsed() : m_clock(0), m_bitsLeft(0) {} |
|
|
|
|
|
LastUsed(clock_t clock, TargetPhraseVectorPtr tpv, size_t bitsLeft = 0) |
|
|
: m_clock(clock), m_tpv(tpv), m_bitsLeft(bitsLeft) {} |
|
|
}; |
|
|
|
|
|
typedef std::map<Phrase, LastUsed> CacheMap; |
|
|
static boost::thread_specific_ptr<CacheMap> m_phraseCache; |
|
|
|
|
|
public: |
|
|
|
|
|
typedef CacheMap::iterator iterator; |
|
|
typedef CacheMap::const_iterator const_iterator; |
|
|
|
|
|
TargetPhraseCollectionCache(size_t max = 5000, float tolerance = 0.2) |
|
|
: m_max(max), m_tolerance(tolerance) { |
|
|
} |
|
|
|
|
|
iterator Begin() { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
return m_phraseCache->begin(); |
|
|
} |
|
|
|
|
|
const_iterator Begin() const { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
return m_phraseCache->begin(); |
|
|
} |
|
|
|
|
|
iterator End() { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
return m_phraseCache->end(); |
|
|
} |
|
|
|
|
|
const_iterator End() const { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
return m_phraseCache->end(); |
|
|
} |
|
|
|
|
|
|
|
|
void Cache(const Phrase &sourcePhrase, TargetPhraseVectorPtr tpv, |
|
|
size_t bitsLeft = 0, size_t maxRank = 0) { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
|
|
|
iterator it = m_phraseCache->find(sourcePhrase); |
|
|
if(it != m_phraseCache->end()) |
|
|
|
|
|
it->second.m_clock = clock(); |
|
|
else { |
|
|
|
|
|
if(maxRank && tpv->size() > maxRank) { |
|
|
TargetPhraseVectorPtr tpv_temp(new TargetPhraseVector()); |
|
|
tpv_temp->resize(maxRank); |
|
|
std::copy(tpv->begin(), tpv->begin() + maxRank, tpv_temp->begin()); |
|
|
(*m_phraseCache)[sourcePhrase] = LastUsed(clock(), tpv_temp, bitsLeft); |
|
|
} else |
|
|
(*m_phraseCache)[sourcePhrase] = LastUsed(clock(), tpv, bitsLeft); |
|
|
} |
|
|
} |
|
|
|
|
|
std::pair<TargetPhraseVectorPtr, size_t> Retrieve(const Phrase &sourcePhrase) { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
iterator it = m_phraseCache->find(sourcePhrase); |
|
|
if(it != m_phraseCache->end()) { |
|
|
LastUsed &lu = it->second; |
|
|
lu.m_clock = clock(); |
|
|
return std::make_pair(lu.m_tpv, lu.m_bitsLeft); |
|
|
} else |
|
|
return std::make_pair(TargetPhraseVectorPtr(), 0); |
|
|
} |
|
|
|
|
|
|
|
|
void Prune() { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
if(m_phraseCache->size() > m_max * (1 + m_tolerance)) { |
|
|
typedef std::set<std::pair<clock_t, Phrase> > Cands; |
|
|
Cands cands; |
|
|
for(CacheMap::iterator it = m_phraseCache->begin(); |
|
|
it != m_phraseCache->end(); it++) { |
|
|
LastUsed &lu = it->second; |
|
|
cands.insert(std::make_pair(lu.m_clock, it->first)); |
|
|
} |
|
|
|
|
|
for(Cands::iterator it = cands.begin(); it != cands.end(); it++) { |
|
|
const Phrase& p = it->second; |
|
|
m_phraseCache->erase(p); |
|
|
|
|
|
if(m_phraseCache->size() < (m_max * (1 - m_tolerance))) |
|
|
break; |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
void CleanUp() { |
|
|
if(!m_phraseCache.get()) |
|
|
m_phraseCache.reset(new CacheMap()); |
|
|
m_phraseCache->clear(); |
|
|
} |
|
|
|
|
|
}; |
|
|
|
|
|
} |
|
|
|
|
|
#endif |
|
|
|