-
-
Save Ninputer/2227226 to your computer and use it in GitHub Desktop.
//请实现下面的函数,输入参数baseStr是一个(可以更改的)字符串,请将其中所有连续出现的多个空格都替换成一个空格,单一空格需保留。 | |
//请直接使用baseStr的空间,如需开辟新的存储空间,不能超过o(N)(注意是小o,N是字符串的长度)。返回值是替换后的字符串的长度。 | |
//样例代码为C#,但可以使用任何语言。如需使用任何库函数,必须同时给出库函数的实现。 | |
class Program | |
{ | |
public static int RemoveMultipleSpaces(char[] baseStr) | |
{ | |
if (baseStr == null) | |
{ | |
throw new ArgumentNullException("baseStr"); | |
} | |
int writeCursor = 0; | |
bool isLastCharSpace = false; | |
for (int i = 0; i < baseStr.Length; i++) | |
{ | |
char current = baseStr[i]; | |
if (current == ' ') | |
{ | |
if (!isLastCharSpace) | |
{ | |
isLastCharSpace = true; | |
baseStr[writeCursor++] = current; | |
} | |
} | |
else | |
{ | |
isLastCharSpace = false; | |
baseStr[writeCursor++] = current; | |
} | |
} | |
return writeCursor; | |
} | |
} | |
//样例测试程序(请自行补充更多的测试案例) | |
[TestFixture] | |
public class ScannersTest | |
{ | |
[Test] | |
public void RemoveOneInnterSpaceBlockTest() | |
{ | |
char[] input = "abc def".ToCharArray(); | |
int resultLength = Program.RemoveMultipleSpaces(input); | |
Assert.AreEqual(7, resultLength); | |
Assert.AreEqual("abc def", new string(input, 0, resultLength)); | |
} | |
[Test] | |
public void RemoveTwoInnterSpaceBlocksTest() | |
{ | |
char[] input = "abc def ghi".ToCharArray(); | |
int resultLength = Program.RemoveMultipleSpaces(input); | |
Assert.AreEqual(11, resultLength); | |
Assert.AreEqual("abc def ghi", new string(input, 0, resultLength)); | |
} | |
[Test] | |
public void KeepSingleSpaceTest() | |
{ | |
char[] input = " a b d e ".ToCharArray(); | |
int resultLength = Program.RemoveMultipleSpaces(input); | |
Assert.AreEqual(9, resultLength); | |
Assert.AreEqual(" a b d e ", new string(input, 0, resultLength)); | |
} | |
[Test] | |
public void AllSpacesTest() | |
{ | |
char[] input = " ".ToCharArray(); | |
int resultLength = Program.RemoveMultipleSpaces(input); | |
Assert.AreEqual(1, resultLength); | |
Assert.AreEqual(" ", new string(input, 0, resultLength)); | |
} | |
} |
http://gist.github.com/2236963
看谁的短!(在 C++ 上用原位修改 + DFA 可以做到 Θ(1) 额外空间,Θ(n) 时间)
Time O(n)
Space O(1)
public static char[] RemoveMultipleSpaces(char[] baseStr)
{
if (baseStr == null)
{
throw new ArgumentNullException("baseStr");
}
if (baseStr.Length == 1)
{
return baseStr;
}
int currentIndex = 0;
int nextIndex = 0;
bool handing = false;
while (nextIndex < baseStr.Length - 1)
{
if (baseStr[nextIndex] == ' ')
{
if (handing)
{
nextIndex++;
continue;
}
else
{
nextIndex++;
baseStr[currentIndex++] = ' ';
handing = true;
}
}
else
{
handing = false;
baseStr[currentIndex++] = baseStr[nextIndex++];
}
}
unsafe
{
fixed (char* c = baseStr)
{
int* i = (int*)c;
*(i - 1) = currentIndex;
}
}
return baseStr;
}
//Test Code
static void Main(string[] args)
{
char[] input = "abc def".ToCharArray();
var output = RemoveMultipleSpaces(input);
input = "abc def ghi".ToCharArray();
output = RemoveMultipleSpaces(input);
input = " a b d e ".ToCharArray();
output = RemoveMultipleSpaces(input);
input = " ".ToCharArray();
output = RemoveMultipleSpaces(input);
input = " ".ToCharArray();
output = RemoveMultipleSpaces(input);
input = "a".ToCharArray();
output = RemoveMultipleSpaces(input);
}
新手特来取经的(俺写的跟大家没法比啊,忒长了),C语言 https://gist.github.com/2238742
$str ='a bc d e f g';
RemoveSpace($str);
function RemoveSpace($str){
/* 获取字符串长度/转为循环次数 /
$l=strlen($str);
for($i=0;$i<$l;$i++){
/ 判断如果当前字符和下一个字符为空格,则当前字符为NUll /
if($str[$i] == ' ' and $str[$i+1] == ' '){
$str[$i] = '';
/ 若不满足条件则认为该字符不是空格,输出该字符串 */
}else{
echo $str[$i];
}
}
}
怎么我的回复没有缩进呢?
public static int RemoteMultipleSpaces(char[] baseStr)
{
if (baseStr == null || baseStr.Length == 0) return 0;
bool previousIsSpace = false;
const char space = ' ';
int originalLength = baseStr.Length;
// how many times have been moved
int movedTimes = 0;
for (int i = 0; i < originalLength - movedTimes; ++i)
{
if (baseStr[i] == space)
{
if (previousIsSpace)
{
// move the following chars to its previous position
for (int j = i; j < originalLength - 1 - movedTimes; j++)
{
baseStr[j] = baseStr[j + 1];
}
// moved once
++movedTimes;
// need to recalculate the index
--i;
}
else
previousIsSpace = true;
}
else
previousIsSpace = false;
}
Array.Copy(baseStr, baseStr, originalLength - movedTimes);
return originalLength - movedTimes;
}
static int RemoveMultipleSpaces(char[] baseStr)
{
int cnt = 0;
bool flag = false;
for (var i = 0; i < baseStr.Length; i++)
{
if (baseStr[i] == ' ')
{
if (flag)
{
cnt++;
}
else
{
flag = true;
if (cnt > 0)
{
baseStr[i - cnt] = baseStr[i];
}
}
}
else
{
if (cnt > 0)
{
baseStr[i - cnt] = baseStr[i];
}
if (flag)
{
flag = false;
}
}
}
return baseStr.Length - cnt;
}
不知道脑袋这个题目的用意。
传递的传输一个对象的引用,而很多写的版本是传的指针,有的甚至连测试代码都改了,方法的定义也改了。
数组对象本身已经在堆上了,如何更改其长度?如果不能修改baseStr的长度,这种替换也没有意义啊,而且测试里也没有测试 替换后的长度是否和返回的长度一致?
因为baseStr是参数啊,所以就等同指针认为了吧,怎么都不能改啊,再说返回的长度不就可以从新截取了吗?当然如果在返回前将baseStr[p]='\0'的话有些情况还是有用的。可惜不会C#,所以不知道它应该怎么处理字符串和字符数组的。。。
可以直接返回一个char[]或 这参数和返回都是string 或者用ref
在c#里 引用类型是地址这和指针不同,方法调用会拷贝对象的引用,这样如果重新给引用地址赋值是没用的。如果是ref 就是指针的效果
public static int RemoveMultipleSpaces(char[] baseStr)
{
int l = 0;
int spaceCount = 0;
int totalSpaceCount = 0;
for (int i = 0; i < baseStr.Length; i++)
{
if (baseStr[i] == ' ')
{
spaceCount++;
}
else
{
l++;
if (spaceCount > 0)
{
l++;
totalSpaceCount += spaceCount - 1;
spaceCount = 0;
}
if (totalSpaceCount > 0)
{
baseStr[i - totalSpaceCount] = baseStr[i];
baseStr[i] = ' ';
}
}
}
if (spaceCount > 0)
{
l++;
}
return l;
}
//请实现下面的函数,输入参数baseStr是一个(可以更改的)字符串,请将其中所有连续出现的多个空格都替换成一个空格,单一空格需保留。
//请直接使用baseStr的空间,如需开辟新的存储空间,不能超过o(N)(注意是小o,N是字符串的长度)。返回值是替换后的字符串的长度。
//样例代码为C#,但可以使用任何语言。如需使用任何库函数,必须同时给出库函数的实现。
class Program
{
public static int RemoveMultipleSpaces(char[] baseStr)
{
// TODO
bool lastisspace=false;
int lastnospace=0;
if(basestr==null ||basestr.length==0){
return 0;
}
int i=0;
for(i=0;i<basestr.length;i++){
if(lastisspace && basestr[i]==' '){
int t=i;
//不使用额外空间,就多花掉时间吧
while(t<basestr.length){
if(basestr[t++]!=' '){
basestr[i]=basestr[t];
basestr[t]=' ';
break;
}
}
if(t+1=basestr.length){
break;
}
lastisspace=false;
}
else if(basestr[i]==' '){
lastisspace=true;
}
else{
lastisspace=false;
}
}
//字符数组的多余空格已经被移到了末尾,从数组index 0开始截取 i个字符即为处理后的字符串数组。
return i;
}
}
// 纯手写,不保证通过,嘿嘿,我是想不到更好的办法,不多申请空间来处理这个了。另外申请个空间处理效率会高一些吧。
include "stdio.h"
include "stdbool.h"
int RemoveMultipleSpaces(char* baseStr)
{
char* s=baseStr;
char* d=baseStr;
if(baseStr==NULL)
return -1;
if(*baseStr=='\0')
return 0;
do{
if(*d==' ')
{
if(s==d || *s==' ')
{
s++;
}
else
{
d++;
*d=*s;
s++;
}
}
else
{
if(d < s)
{
d++;
*d=*s;
s++;
}
else
{
s++;
d++;
}
}
}while((*d)!='\0');
return d-baseStr;
}
int main(int argc,char\* argv[]) { int i=0; int len=0; char test[7][30]={ {"abc def"}, {"abc def"}, { "abc def ghi"}, { " a b d e "}, { " a b d e "}, { " "}, { ""}, }; ``` for(i=0;i<7;i++) { printf("test[%d]:%s|\t",i,test[i]); len=RemoveMultipleSpaces(test[i]); printf("after:len=%d,test=%s|\n",len,test[i]); } return 0; ``` } ===结果=== test[0]:abc def| after:len=7,test=abc def| test[1]:abc def| after:len=7,test=abc def| test[2]:abc def ghi| after:len=11,test=abc def ghi| test[3]: a b d e | after:len=9,test= a b d e | test[4]: a b d e | after:len=9,test= a b d e | test[5]: | after:len=1,test= | test[6]:| after:len=0,test=|
public static int RemoveMultipleSpaces(char[] baseStr)
{
// TODO
int length = 0;
char tmp = new char();
for (int i = 0; i < baseStr.Length; i++)
{
if (baseStr[i] == ' ')
{
if (tmp != baseStr[i])
{
length++;
}
}
else
{
length++;
}
tmp = baseStr[i];
}
return length;
}
这样对吧~ 测试了应该是说的这个问题吧,有的把简单的搞复杂了!