我正在创建一个新的简单应用程序来标记和删除给定文本中的停止词。为此,我创建了以下文件:
// Stopword.js
class StopWord {
constructor (stopWords) {
this.stopWords = stopWords
}
remove (value) {
// do whatever we need to remove this.stopWords from the passed value and return it
}
}// PreProcess.js
const StopWord = require('./StopWord')
class PreProcess {
setValue (value) {
this.value = value
return this
}
removeStopWords (stopWords) {
const stopWord = new StopWord(stopWords)
return stopWord.remove(this.value)
}
}// Indexed.js
class Indexer {
setValue (value) {
this.value = value
return this
}
setStopWords (stopWords) {
this.stopWords = stopWords
return this
}
index () {
return this.preprocess
.setValue(this.value)
.removeStopWords(stopWords)
}
}// main.js
const indexer = new Indexer()
const result = indexer
.setValue('a sample text ')
.setStopWords(['a', 'an'])
.index()
console.log(result)假设在某些情况下,我们希望动态地从数据库加载停止词(不同用户的停止词不同)。出现的第一个问题是,我们需要在哪个类中从数据库加载停止单词?显然,类PreProcess是使用依赖注入注入索引的。类StopWord也可以使用DI注入,但我想知道这是否足够好。第二个问题是,应该将哪些类注入哪一类?
发布于 2019-05-23 18:24:01
不要试图根据需要使事情变得更复杂:-)从您目前的名称来看,我不知道如何使用该功能。什么是索引器?什么是预处理器?那些东西可能是任何东西。因此,让它保持简单,从域的角度直接到重点(我将在TypeScript中给出示例,这样您就可以看到在哪里使用了哪些类型):
首先,我们将定义停止词域服务(业务域):
/** we'll use this to provide stop words as array of strings */
class StopWords {
public stopWords: string[] = [];
constructor(words?: string[]) { this.stopWords = words }
}
/** single responsibility of this class: actually remove the stopwords */
class StopWordsRemovalService {
/** inject stopwords through constructor */
constructor(stopWords: StopWords) {}
/** here we do the real removal work */
public removeAllStopWordsFrom(text: string): string { return ''; }
}现在,我们可以从任何位置(基础设施方面的更多信息)提供停止词:
/** TypeScript provids interfaces, which you don't have in plain JS. It merely
* defines the class method signatures, which is quite useful in software design */
interface StopWordsProvider {
getStopWords(): StopWords;
}
class DefaultStopWordsProvider implements StopWordsProvider {
getStopWords(): StopWords {
return new StopWords(['a', 'an']);
}
}
class DbStopWordsProvider implements StopWordsProvider {
getStopWords(): StopWords {
return db.query("SELECT stopWords FROM ...");
}
}最后,我们将连接在一起:
const swremoval: StopWordsRemovalService = new StopWordsRemovalService(new DefaultStopWordsProvider().getStopWords());
swremoval.removeAllStopWordsFrom('a sample text');要将事情连接在一起,现在可以使用依赖项注入框架(如InversifyJS )。
更新:我们需要通过用户ID返回不同的停止词。
我在这里想到的第一个问题是,用户ID对业务有多重要?如果总是需要用户ID来确定停止词,则用户ID是我们域的一个组成部分!如果有时需要用户ID来确定停止词,则它可能不是我们域的一个组成部分。让我们来研究这两种情况:
检索停止词总是需要用户ID。
如果用户ID对域很重要,并且总是需要确定停止词,那么让我们将其作为契约的一部分:
/** TypeScript provids interfaces, which you don't have in plain JS. It merely
* defines the class method signatures, which is quite useful in software design */
interface StopWordsProvider {
/** Returns all the stop words for the given user */
getStopWords(userID: number): StopWords;
}现在,实现此接口的所有类都需要尊重用户ID。
有时需要用户ID来检索停止词。
如果某些查找只需要用户ID,我们将不会更改停止词契约(即界面)!相反,我们将提供一个执行查找的UserSpecificStopWordsProvider。要配置用户ID,我们将使用工厂模式:
/** The user-specific stopwords provider is configured through
* constructor-based injection */
class UserSpecificStopWordsProvider implements StopWordsProvider {
constructor(private userId: number) {}
getStopWords(): StopWords {
return db.query("SELECT * FROM sw WHERE userId = :userId", this.userId);
}
}
/** To simplify the usage, we'll provide a factory to do this. */
class UserSpecificStopWordsProviderFactory {
factoryProvider(userId: number): StopWordsProvider {
// potentially inject more dependencies here
return new UserSpecificStopWordsProvider(userId);
}
}
/** We can then use it as follows: */
const factory = new UserSpecificStopWordsProviderFactory();
factory.factoryProvider(5).getStopWords();https://stackoverflow.com/questions/56276532
复制相似问题