Skip to content

Commit bd8f46b

Browse files
authored
feat: add solutions to lc problem: No.2047 (#3368)
No.2047.Number of Valid Words in a Sentence
1 parent 238a419 commit bd8f46b

File tree

7 files changed

+405
-184
lines changed

7 files changed

+405
-184
lines changed

solution/2000-2099/2047.Number of Valid Words in a Sentence/README.md

+144-61
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,25 @@ tags:
7777

7878
<!-- solution:start -->
7979

80-
### 方法一
80+
### 方法一:模拟
81+
82+
我们首先将句子按空格分割成单词,然后对每个单词进行检查,判断是否为有效单词。
83+
84+
对于每个单词,我们可以使用一个布尔变量 $\textit{st}$ 来记录是否已经出现过连字符,然后遍历单词中的每个字符,根据题目描述的规则进行判断。
85+
86+
对于每个字符 $s[i]$,我们有以下几种情况:
87+
88+
- 如果 $s[i]$ 是数字,那么 $s$ 不是有效单词,直接返回 $\text{false}$;
89+
- 如果 $s[i]$ 是标点符号('!'、'.'、',')且 $i < \text{len}(s) - 1$,那么 $s$ 不是有效单词,直接返回 $\text{false}$;
90+
- 如果 $s[i]$ 是连字符,那么我们需要判断是否满足以下条件:
91+
- 连字符只能出现一次;
92+
- 连字符不能出现在单词的开头或结尾;
93+
- 连字符两侧必须是字母;
94+
- 如果 $s[i]$ 是字母,那么我们不需要做任何处理。
95+
96+
最后,我们统计出句子中的有效单词数即可。
97+
98+
时间复杂度 $O(n)$,空间复杂度 $O(n)$。其中 $n$ 是句子的长度。
8199

82100
<!-- tabs:start -->
83101

@@ -86,24 +104,23 @@ tags:
86104
```python
87105
class Solution:
88106
def countValidWords(self, sentence: str) -> int:
89-
def check(token):
90-
hyphen = False
91-
for i, c in enumerate(token):
92-
if c.isdigit() or (c in '!.,' and i < len(token) - 1):
107+
def check(s: str) -> bool:
108+
st = False
109+
for i, c in enumerate(s):
110+
if c.isdigit() or (c in "!.," and i < len(s) - 1):
93111
return False
94-
if c == '-':
112+
if c == "-":
95113
if (
96-
hyphen
97-
or i == 0
98-
or i == len(token) - 1
99-
or not token[i - 1].islower()
100-
or not token[i + 1].islower()
114+
st
115+
or i in (0, len(s) - 1)
116+
or not s[i - 1].isalpha()
117+
or not s[i + 1].isalpha()
101118
):
102119
return False
103-
hyphen = True
120+
st = True
104121
return True
105122

106-
return sum(check(token) for token in sentence.split())
123+
return sum(check(s) for s in sentence.split())
107124
```
108125

109126
#### Java
@@ -112,76 +129,142 @@ class Solution:
112129
class Solution {
113130
public int countValidWords(String sentence) {
114131
int ans = 0;
115-
for (String token : sentence.split(" ")) {
116-
if (check(token)) {
117-
++ans;
118-
}
132+
for (String s : sentence.split(" ")) {
133+
ans += check(s.toCharArray());
119134
}
120135
return ans;
121136
}
122137

123-
private boolean check(String token) {
124-
int n = token.length();
125-
if (n == 0) {
126-
return false;
138+
private int check(char[] s) {
139+
if (s.length == 0) {
140+
return 0;
127141
}
128-
boolean hyphen = false;
129-
for (int i = 0; i < n; ++i) {
130-
char c = token.charAt(i);
131-
if (Character.isDigit(c) || (i < n - 1 && (c == '!' || c == '.' || c == ','))) {
132-
return false;
142+
boolean st = false;
143+
for (int i = 0; i < s.length; ++i) {
144+
if (Character.isDigit(s[i])) {
145+
return 0;
146+
}
147+
if ((s[i] == '!' || s[i] == '.' || s[i] == ',') && i < s.length - 1) {
148+
return 0;
133149
}
134-
if (c == '-') {
135-
if (hyphen || i == 0 || i == n - 1 || !Character.isLetter(token.charAt(i - 1))
136-
|| !Character.isLetter(token.charAt(i + 1))) {
137-
return false;
150+
if (s[i] == '-') {
151+
if (st || i == 0 || i == s.length - 1) {
152+
return 0;
138153
}
139-
hyphen = true;
154+
if (!Character.isAlphabetic(s[i - 1]) || !Character.isAlphabetic(s[i + 1])) {
155+
return 0;
156+
}
157+
st = true;
140158
}
141159
}
142-
return true;
160+
return 1;
143161
}
144162
}
145163
```
146164

147-
#### TypeScript
165+
#### C++
148166

149-
```ts
150-
function countValidWords(sentence: string): number {
151-
let words = sentence.trim().split(/\s+/);
152-
let ans = 0;
153-
for (let word of words) {
154-
if (isValied(word)) {
155-
ans++;
167+
```cpp
168+
class Solution {
169+
public:
170+
int countValidWords(string sentence) {
171+
auto check = [](const string& s) -> int {
172+
bool st = false;
173+
for (int i = 0; i < s.length(); ++i) {
174+
if (isdigit(s[i])) {
175+
return 0;
176+
}
177+
if ((s[i] == '!' || s[i] == '.' || s[i] == ',') && i < s.length() - 1) {
178+
return 0;
179+
}
180+
if (s[i] == '-') {
181+
if (st || i == 0 || i == s.length() - 1) {
182+
return 0;
183+
}
184+
if (!isalpha(s[i - 1]) || !isalpha(s[i + 1])) {
185+
return 0;
186+
}
187+
st = true;
188+
}
189+
}
190+
return 1;
191+
};
192+
193+
int ans = 0;
194+
stringstream ss(sentence);
195+
string s;
196+
while (ss >> s) {
197+
ans += check(s);
156198
}
199+
return ans;
157200
}
158-
return ans;
201+
};
202+
```
203+
204+
#### Go
205+
206+
```go
207+
func countValidWords(sentence string) (ans int) {
208+
check := func(s string) int {
209+
if len(s) == 0 {
210+
return 0
211+
}
212+
st := false
213+
for i, r := range s {
214+
if unicode.IsDigit(r) {
215+
return 0
216+
}
217+
if (r == '!' || r == '.' || r == ',') && i < len(s)-1 {
218+
return 0
219+
}
220+
if r == '-' {
221+
if st || i == 0 || i == len(s)-1 {
222+
return 0
223+
}
224+
if !unicode.IsLetter(rune(s[i-1])) || !unicode.IsLetter(rune(s[i+1])) {
225+
return 0
226+
}
227+
st = true
228+
}
229+
}
230+
return 1
231+
}
232+
for _, s := range strings.Fields(sentence) {
233+
ans += check(s)
234+
}
235+
return ans
159236
}
237+
```
238+
239+
#### TypeScript
160240

161-
function isValied(str: string): boolean {
162-
let n = str.length;
163-
let hasLine = false;
164-
for (let i = 0; i < n; i++) {
165-
const char = str.charAt(i);
166-
if (/^[0-9]$/.test(char)) {
167-
return false;
241+
```ts
242+
function countValidWords(sentence: string): number {
243+
const check = (s: string): number => {
244+
if (s.length === 0) {
245+
return 0;
168246
}
169-
if (char == '-') {
170-
if (hasLine) return false;
171-
else {
172-
hasLine = true;
247+
let st = false;
248+
for (let i = 0; i < s.length; ++i) {
249+
if (/\d/.test(s[i])) {
250+
return 0;
173251
}
174-
let pre = str.charAt(i - 1),
175-
post = str.charAt(i + 1);
176-
if (!/^[a-z]$/g.test(pre) || !/^[a-z]$/g.test(post)) {
177-
return false;
252+
if (['!', '.', ','].includes(s[i]) && i < s.length - 1) {
253+
return 0;
254+
}
255+
if (s[i] === '-') {
256+
if (st || [0, s.length - 1].includes(i)) {
257+
return 0;
258+
}
259+
if (!/[a-zA-Z]/.test(s[i - 1]) || !/[a-zA-Z]/.test(s[i + 1])) {
260+
return 0;
261+
}
262+
st = true;
178263
}
179264
}
180-
if (/^[\!\.\,\s]$/.test(char) && i != n - 1) {
181-
return false;
182-
}
183-
}
184-
return true;
265+
return 1;
266+
};
267+
return sentence.split(/\s+/).reduce((acc, s) => acc + check(s), 0);
185268
}
186269
```
187270

0 commit comments

Comments
 (0)