写一个方法:
public String delString(String A,String B){
.....方法体......
}
用高效的方式从A中剔除包含B的字符,例如String A="hi are you ok";
String B="io";delString方法返回"h are yu k"
注意:不能使用String的instand of ,splid,char at等等库函数
请问怎么做?
public String delString(String A,String B){
.....方法体......
}
用高效的方式从A中剔除包含B的字符,例如String A="hi are you ok";
String B="io";delString方法返回"h are yu k"
注意:不能使用String的instand of ,splid,char at等等库函数
请问怎么做?
如果在b里存在,就什么都不做
不存在 加到一个的stringbuffer中
看错题了。
import java.util.regex.Matcher;
import java.util.regex.Pattern;public class DelString {
public static void main(String args[]){
String regEx = "i+|o+";
String str = "hi are you ok";
Pattern p=Pattern.compile(regEx);
Matcher m=p.matcher(str);
String s = m.replaceAll("");
System.out.println(s);
}
}
char[] charA = A.toCharArray();
char[] charB = B.toCharArray();
char[] temp=new char[charA.length];
for(int i=0;i<charB.length;i++){
map.put(charB[i],"");
}
int k=0;
for(int j=0;j<charA.length;j++){
if(map.get(charA[j])==null){
temp[k++]=charA[j];
}
}
return new String(temp).trim();
}
public String delString(String A, String B) {
StringBuffer sb = new StringBuffer(A);
StringBuffer sb1 = new StringBuffer(B);
for (int i = 0; i < sb.length(); i++) {
for (int j = 0; j < sb1.length(); j++) {
if (sb.charAt(i) == sb1.charAt(j)) {
sb.deleteCharAt(i);
}
}
}
A = sb.toString();
return A;
}我用的是:StringBuffer的charAt函数,我用他做了10已次的循环,平均执行一次delString2千多ns
应该就是转换成数组后处理吧。
按照楼主的要求,直接用数组对比,发现一个剔除一个,char数组的copy。
应该是O2n吧
String a = "hi are you ok";
String b = "io";
long t0, t1;
String s = null;
t0 = System.nanoTime();
s = delString(a, b);
t1 = System.nanoTime();
System.out.println(t1 - t0 + " ns");
System.out.println(s);
}
private static String delString(String a, String b) {
char[] ca = a.toCharArray();
char[] cb = b.toCharArray();
char[] c = new char[ca.length];
int len = 0;
for(int i = 0; i < ca.length; i++) {
boolean isExist = false;
for(int j = 0; j < cb.length; j++) {
if(ca[i] == cb[j]) {
isExist = true;
break;
}
}
if(!isExist) {
c[len++] = ca[i];
}
}
return new String(c, 0, len);
}
}
===============================
注意:不能使用String的instand of ,splid,char at等等库函数
他都說了String的庫函數都不能用嗎,那我只能想到el了
用js可以嗎?
。写一个方法:
public String delString(String A,String B){
.....方法体......
}
這是他本來就有的,給你的,教你補完,還是你自己寫的?
String del="";
char [] c=A.toCharArray();
char [] d=B.toCharArray();
Set<char>set=new HashSet<char>();
for(char x:d){
set.add(x);
}
int i=set.size();
for(char s:c){
set.add(s);
if(set.size()==i){
continue;
}
del=del+s;
}
return del;
}
char[] ca = a.toCharArray();
char[] cb = b.toCharArray();
char[] c = new char[ca.length];
int len = 0;
for(int i = 0; i < ca.length; i++) {
boolean isExist = false;
for(int j = 0; j < cb.length; j++) {
if(ca[i] == cb[j]) {
isExist = true;
break;
}
}
if(!isExist) {
c[len++] = ca[i];
}
}
return new String(c, 0, len);
}
就可以了,,实现还是简单的,当年学c语言的时候就经常干这种事,,
每想到现在还让干,看来基础很 简单呀,,
记得以前还有个题目也是这样的
写一个方法:
public String delString(String A,String B){
.....方法体......
}
用高效的方式从A中剔除包含B的字符,例如String A="I love you!";
String B="ov";delString方法返回"I le you"
注意:不能使用String的instand of ,splid,char at等等库函数
请问怎么做?
呵呵,,大家接着来呀,哈哈啊
char[] ca = a.toCharArray();
char[] cb = b.toCharArray();
char[] c = new char[ca.length];
int len = 0;
for(int i = 0; i < ca.length; i++) {
boolean isExist = false;
for(int j = 0; j < cb.length; j++) {
if(ca[i] == cb[j]) {
isExist = true;
break;
}
}
if(!isExist) {
c[len++] = ca[i];
}
}
return new String(c, 0, len);
}
就可以了,,实现还是简单的,当年学c语言的时候就经常干这种事,,
每想到现在还让干,看来基础很 简单呀,,
记得以前还有个题目也是这样的
写一个方法:
public String delString(String A,String B){
.....方法体......
}
用高效的方式从A中剔除包含B的字符,例如String A="I love you!";
String B="ov";delString方法返回"I le you"
注意:不能使用String的instand of ,splid,char at等等库函数
请问怎么做?
呵呵,,大家接着来呀,哈哈啊
代码如下:public class DelString { public String del(String a, String b){
char[] aChar=a.toCharArray();
char[] bChar=b.toCharArray();
long pattern=0;
for(char c:bChar){//获得b组成的pattern
pattern+=getValue(c);
}
StringBuffer result=new StringBuffer();
for(char c:aChar){ //遍历a,查看是否由b中的字符
long value=getValue(c);
if((value&pattern)>0){
continue;
}
result.append(c);
}
return result.toString();
}
public long getValue(char c){
int span=c-65; //'A'字符值为65
long value=1;
value=value<<span;
return value;
}
public static void main(String[] args) {
DelString test=new DelString();
System.out.println(test.del("hi are you ok", "io"));
}
}算法的主要思想是使用占位符
--------------------------------------------------------------------------------超时时间已到。在操作完成之前超时时间已过或服务器未响应。
说明: 执行当前 Web 请求期间,出现未处理的异常。请检查堆栈跟踪信息,以了解有关该错误以及代码中导致错误的出处的详细信息。 异常详细信息: System.Data.SqlClient.SqlException: 超时时间已到。在操作完成之前超时时间已过或服务器未响应。源错误: 执行当前 Web 请求期间生成了未处理的异常。可以使用下面的异常堆栈跟踪信息确定有关异常原因和发生位置的信息。 堆栈跟踪:
[SqlException (0x80131904): 超时时间已到。在操作完成之前超时时间已过或服务器未响应。]
System.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, Boolean breakConnection) +800131
System.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj) +186
System.Data.SqlClient.TdsParserStateObject.ReadSniError(TdsParserStateObject stateObj, UInt32 error) +556
System.Data.SqlClient.TdsParserStateObject.ReadSni(DbAsyncResult asyncResult, TdsParserStateObject stateObj) +164
System.Data.SqlClient.TdsParserStateObject.ReadPacket(Int32 bytesExpected) +34
System.Data.SqlClient.TdsParserStateObject.ReadBuffer() +44
System.Data.SqlClient.TdsParserStateObject.ReadByte() +17
System.Data.SqlClient.TdsParser.Run(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj) +79
System.Data.SqlClient.SqlDataReader.ConsumeMetaData() +31
System.Data.SqlClient.SqlDataReader.get_MetaData() +62
System.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString) +297
System.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean async) +1005
System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method, DbAsyncResult result) +132
System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method) +32
System.Data.SqlClient.SqlCommand.ExecuteReader(CommandBehavior behavior, String method) +122
System.Data.SqlClient.SqlCommand.ExecuteReader() +84
CSDN.Community.TopicDatabase.TopicDataProvider_PointForum.pointForum_ReplyTopic(ReplyInfo reply, String& ErrInfo, TopicInfo& topic) +775
CSDN.Community.PointForum.Services.ReplyTopicManager.ReplyTopic(ReplyInfo reply, DateTime topicPostDate, String& errorInfo, CommunityUser user, UserSectionProfile usp) +419
CSDN.Community.PointForum.WebControls.ReplyTopicPage.bt_Submit_Click(Object sender, EventArgs e) +604
System.Web.UI.WebControls.Button.OnClick(EventArgs e) +105
System.Web.UI.WebControls.Button.RaisePostBackEvent(String eventArgument) +107
System.Web.UI.WebControls.Button.System.Web.UI.IPostBackEventHandler.RaisePostBackEvent(String eventArgument) +7
System.Web.UI.Page.RaisePostBackEvent(IPostBackEventHandler sourceControl, String eventArgument) +11
System.Web.UI.Page.RaisePostBackEvent(NameValueCollection postData) +33
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +1746
--------------------------------------------------------------------------------
版本信息: Microsoft .NET Framework 版本:2.0.50727.1433; ASP.NET 版本:2.0.50727.1433
public class Test {
public static void main(String[] args) {
Test t = new Test();
System.out.println(t.delStrubg("hello world", "ol"));
} public String delStrubg(String a, String b) {
return a.replaceAll("[" + b + "]", "");
}
}
int max = Integer.MIN_VALUE;
for( char ch : b ) {
if( max < (int)ch ) {
max = (int)ch;
}
}
for( char ch : a ) {
if( max < (int)ch ) {
max = (int)ch;
}
}
int [] arrayA = new int [max + 1];
int [] arrayB = new int [max + 1];
for( char ch : a ) {
arrayA[(int)ch]++;
}
for( char ch : b) {
arrayB[(int)ch]++;
}
for( int i = 0; i < max; i++ ) {
if( arrayA[i] != 0 && arrayB[i] != 0 ) {
arrayA[i] = 0;
}
}
String s = "";
for( int i = 0; i < a.length; i++ ) {
if( arrayA[(int)a[i]] != 0 ) s += a[i];
}
return s;
}
public void testXixi() {
String A="hi are you ok";
String B="io";
System.out.println( this.delString(A.toCharArray(), B.toCharArray()) );
}算法分析:
这个算法相当浪费空间,但是可以让时间复杂度降到线型
应为如果用迭代得方法,那么时间复杂度是A.length * B.length
但是用这个方法,
我们建立两个int数组,里面储存字母显示字符串A和字符串B的字符的显示的次数
由于两个数组的长度一样,而且对应的index和字符一样,那么只要对比index就可以得出A数组里面有那些字符B里面有,然后把对应的元素的显示次数清零
最后通过数组,把不为零的数组算出来就可以了计算两个数组的长度,算出最大值的时间复杂度是A.length + B.length
计算两个数组里面字符出现的次数的时间复杂度和上面一样
最后清零的时间复杂度是数组的长度(数组最大长度不超过255 because char)
那么最后得出结果的复杂度也<= A.length
最后我们可以算出 O(n)
这个算法最大的毛病是耗费内存,按时节省了很多的时间.
public class Test {
public static void main(String[] args) {
System.out.println(removeByChar("hi are you ok this", "tiooiiot"));
} public static String removeByChar(String str, String removed) {
char[] strs = str.toCharArray();
char[] removeds = removed.toCharArray();
int i, j, m = 0;
char blank = 0x0;
// 循环是免不了的
OUT: for (i = 0; i < removeds.length; i++) {
j = 0;
for (; j < m; j++) {
if (removeds[j] == removeds[i]) {
continue OUT;
}
}
removeds[m++] = removeds[i];
for (j = 0; j < strs.length; j++) {
if (strs[j] == removeds[i]) {
strs[j] = blank;
}
}
}
// 如果需要剔除字符的占位,可以附加这个方法
int resultCount = 0;
for (i = 0; i < strs.length; i++) {
if (strs[i] != blank) {
strs[resultCount++] = strs[i];
}
}
return new String(strs, 0, resultCount);
}
}
for(int i=0;i<A。lentgh;i++){
判断是不是存在"i";
是就删除对应的字符;
for(int j=0;j<A.lentgh;j++){
判断是不是存在"o":
是就删除对应的字符;
}
}
这样就可以过滤了;
3 单点登录
4 输出一个字符串,然后反向输出。string str = "abc";输出 cba5 还有一个多线程的题去了也可能是去做网站,工资估计不高,所以天天在招人。
首先: arrayA[]没有必要存在,只要将原27行起的循环.
for( int i = 0; i < a.length; i++ ) {
if( arrayA[(int)a[i]] != 0 ) s += a[i];
}
改为:
for( int i = 0; i < a.length; i++ ) {
if( arrayB[(int)a[i]] == 0 ) s += a[i];
}
即可以,由此可以删除原22行起的循环
for( int i = 0; i < max; i++ ) {
if( arrayA[i] != 0 && arrayB[i] != 0 ) {
arrayA[i] = 0;
}
}
及有关arrayA[]的相关信息.再者:可以用(int)(a[i]-'a')作为字符与数组下标的对应关系,而不是用(int)a[i],这样可以节省一些内存开销,当然这样做增加了计算减法用的时间开销.
先提一个简单的问题,如果有一个庞大的字符串数组,然后给你一个单独的字符串,让你从这个数组中查找是否有这个字符串并找到它,你会怎么做?有一个方法最简单,老老实实从头查到尾,一个一个比较,直到找到为止,我想只要学过程序设计的人都能把这样一个程序作出来,但要是有程序员把这样的程序交给用户,我只能用无语来评价,或许它真的能工作,但...也只能如此了。最合适的算法自然是使用HashTable(哈希表),先介绍介绍其中的基本知识,所谓Hash,一般是一个整数,通过某种算法,可以把一个字符串"压缩" 成一个整数,这个数称为Hash,当然,无论如何,一个32位整数是无法对应回一个字符串的,但在程序中,两个字符串计算出的Hash值相等的可能非常小,下面看看在MPQ中的Hash算法unsigned long HashString(char *lpszFileName, unsigned long dwHashType)
{
unsigned char *key = (unsigned char *)lpszFileName;
unsigned long seed1 = 0x7FED7FED, seed2 = 0xEEEEEEEE;
int ch;while(*key != 0)
{
ch = toupper(*key++);seed1 = cryptTable[(dwHashType << 8) + ch] ^ (seed1 + seed2);
seed2 = ch + seed1 + seed2 + (seed2 << 5) + 3;
}
return seed1;
}Blizzard的这个算法是非常高效的,被称为"One-Way Hash",举个例子,字符串"unitneutralacritter.grp"通过这个算法得到的结果是0xA26067F3。
是不是把第一个算法改进一下,改成逐个比较字符串的Hash值就可以了呢,答案是,远远不够,要想得到最快的算法,就不能进行逐个的比较,通常是构造一个哈希表(Hash Table)来解决问题,哈希表是一个大数组,这个数组的容量根据程序的要求来定义,例如1024,每一个Hash值通过取模运算 (mod)对应到数组中的一个位置,这样,只要比较这个字符串的哈希值对应的位置又没有被占用,就可以得到最后的结果了,想想这是什么速度?是的,是最快的O(1),现在仔细看看这个算法吧
int GetHashTablePos(char *lpszString, SOMESTRUCTURE *lpTable, int nTableSize)
{
int nHash = HashString(lpszString), nHashPos = nHash % nTableSize;if (lpTable[nHashPos].bExists && !strcmp(lpTable[nHashPos].pString, lpszString))
return nHashPos;
else
return -1; //Error value
}看到此,我想大家都在想一个很严重的问题:"如果两个字符串在哈希表中对应的位置相同怎么办?",毕竟一个数组容量是有限的,这种可能性很大。解决该问题的方法很多,我首先想到的就是用"链表",感谢大学里学的数据结构教会了这个百试百灵的法宝,我遇到的很多算法都可以转化成链表来解决,只要在哈希表的每个入口挂一个链表,保存所有对应的字符串就OK了。事情到此似乎有了完美的结局,如果是把问题独自交给我解决,此时我可能就要开始定义数据结构然后写代码了。然而Blizzard的程序员使用的方法则是更精妙的方法。基本原理就是:他们在哈希表中不是用一个哈希值而是用三个哈希值来校验字符串。中国有句古话"再一再二不能再三再四",看来Blizzard也深得此话的精髓,如果说两个不同的字符串经过一个哈希算法得到的入口点一致有可能,但用三个不同的哈希算法算出的入口点都一致,那几乎可以肯定是不可能的事了,这个几率是1:18889465931478580854784,大概是10的 22.3次方分之一,对一个游戏程序来说足够安全了。现在再回到数据结构上,Blizzard使用的哈希表没有使用链表,而采用"顺延"的方式来解决问题,看看这个算法:
int GetHashTablePos(char *lpszString, MPQHASHTABLE *lpTable, int nTableSize)
{
const int HASH_OFFSET = 0, HASH_A = 1, HASH_B = 2;
int nHash = HashString(lpszString, HASH_OFFSET);
int nHashA = HashString(lpszString, HASH_A);
int nHashB = HashString(lpszString, HASH_B);
int nHashStart = nHash % nTableSize, nHashPos = nHashStart;while (lpTable[nHashPos].bExists)
{
if (lpTable[nHashPos].nHashA == nHashA && lpTable[nHashPos].nHashB == nHashB)
return nHashPos;
else
nHashPos = (nHashPos + 1) % nTableSize;if (nHashPos == nHashStart)
break;
}return -1; //Error value
}
既然是关于字符的,那首先对字符串B的字符建个出现数组bool bToDelete[],
字符的个数总是有限的,比如限制字符是在小写英文字母集合中,那数组大小就开26即可,0-25分别表示字符a-z
bToDelete[0] = 1 表示B中存在字符‘a’,否则表示没有‘a’;
bToDelete[1] = 1 表示B中存在字符‘b’,否则表示没有‘b’;
……
bToDelete[25] = 1 表示B中存在字符‘z’,否则表示没有‘z’;
然后扫描一边字符串B,即可确定bToDelete。接下来扫描一边字符串A,再建一新字符串C保存删除后的结果。
即bToDelete[A[i]-'a']=0,则存入C中。。算法复杂度O(n),不需要平方级别的。
连数组不都取不到?
所以
只有考虑用算法了
42 50楼的不错 不知道有没有更好的
最后骂一句 :SB迅雷。。Bullshit!
为什么这么简单的问题没有人会?我们祖国的下一代还能不能写代码了?
睁大眼看看正确答案吧 @@ public static String delString(String a,String b){
for(char c:b.toCharArray()){
a=a.replaceAll(c+"","");
}
return a;
}
您的方法下界是n的平方。
太慢了,
想速度快,只能空间换时间。
Set=Map方法其实和上面的暴雪崇拜者的方法是一样的。
步骤一 设计一个散列函数可以散列出hashCode,
步骤2 然后把b字符串的所有字符 用这个散列函数计算出一个code,把code当作偏移作为数组下标,把数组的那个偏移的单位标记成true;
步骤3 把a字符串所有字符,计算散列,查看在这个散列作为坐标情况下那个单位的标记是true还是false 是true说明有这个字符,是false说明b字符串中没有a当前这个字符。提供一种简单方法:
{
1 int [] hashtable = new Int32[2<<16];
2 把hashtable里内容置0
3 char[] bchars = B.toCharArray();
4 for(char tempch:bchars)
{ hashtable[(uint)tempch] = 1;}
5 string result="";
6 char[] achars = A.toCharArray();
7 for(char tempaa :achars)
{if(hashtable[(uint)tempaa)]!=1
result += tempaa;
}
8 return result;}
缺陷还是一点,需要开设的空间太大。可能大家不是很清楚,当空间过大需要用到swap虚拟内存时,也许效率会得不偿失。给出一个改进方案:由于b中每个字符都是char(在java中char用unicode编码占2字节),也就是char用16位表示,2的16次方是65536.需要开设65536个空间吗?好像65536不是很大的空间,但是为了构造节约型社会,能省则省。
把65536个标志用的空间,从Int32 降低为bool,也就是说 只需要65536/32=2048个int单元即可。
太晚了具体做法不给出了,有兴趣的可以实现一下,提示:位存储算法和程序是一回事,如果不是这样,程序员真可以当民工了
public static void main(String[] args){
String A="hi are you ok";
String B="io";
String C="["+B+"]";
String D=A.replaceAll(C, "");
out.println(D);
}
}
就把对应的A设为0,最后根据A数组,生成要返回的字符串
{
int i,j;
int IA[256] = {0};
int IB[256] = {0};
char* C;
i = j = 0; while ( A[i] != '\0'){
IA[A[i]]++;
i++;
}
while ( B[j] != '\0' ){
IA[B[j]] = 0;
j++;
}
i = j = 0;
while ( A[i] != '\0' ){
if ( IA[A[i]] == 0 )
i++;
else
C[j++] = A[i++];
}
C[j] = '\0';
return C;
}小弟不太会C++,用C写了个程序,想必转换为C++不难吧
算法复杂度:O(N),N为A的长度
这是我想到最快的方法了,若有更快的方法,希望大侠能和我交流,谢谢!!!!!
E-mail:[email protected]
有的话就是 你这个只能计算ASCII字符 UNICODE字符你怎么办
import java.util.Set;public class Util {
static public void main(String[] strs) {
String strA = "hi are you ok";
String strB = "io";
System.out.println(delString(strA, strB));
}
static public String delString(String strA, String strB) {
char[] charB = strB.toCharArray();
Set setB = new HashSet(charB.length);
for (int i = 0; i < charB.length; i++)
setB.add(charB[i]);
char[] charA = strA.toCharArray();
char[] charC = new char[charA.length];
int j = 0;
for (int i = 0 ; i < charA.length; i++)
if (!setB.contains(charA[i]))
charC[j++] = charA[i];
return new String(charC,0,j);
}
}
char* delString(char* A,char* B)
{
int i,j;
int IA[256] = {0};
int IB[256] = {0};
char* C; i = j = 0; while ( A[i] != '\0'){
IA[A[i]]++;
i++;
}
while ( B[j] != '\0' ){
IA[B[j]] = 0;
j++;
}
i = j = 0;
while ( A[i] != '\0' ){
if ( IA[A[i]] == 0 )
i++;
else
C[j++] = A[i++];
}
C[j] = '\0'; return C;
}
问题1 c未分配空间,char*c,c里面是任意值。给c[j]赋值很有可能会崩溃
问题2 字符集问题,并不是所有字符串都是有\0结束的。unicode是\0\0
所以开256空间是不可行的;
用不相交集来做是根本思路
但不知道java里的set效率如何?达人解释一下?java set的并,交,差操作时间复杂度?
2,题目要求不可以用String的函数replaceAll不可以用。当然转换成char等函数还是可以用。
你自己不看清楚题目,就不要怪别人不理你了。
对于String A中的每个字符ch进行查询,看是否在String B中,不再就(strbuf += ch)将ch放入
缓冲字符串中具体实现就不写了,大家现看看这样可以吗?
如果只有三斤重的东西送到邻居家,步行最快,送到街道,自行车最快,把一百吨的东西送到美国,当然运输机最快.如果源字符串和要查找的字符串都很短,两重循环最快.
如果源串和要查找的字符串都很长,比如源串10万字符,要查找的字符串4万字符,这样两重循环有
40亿次,那么hash表处理最快.把目标串的所有字符放到hash表中,注意包括符号也不过是128个字符而已.把源串的每个字符去拚到StringBuffer或数组之前,先去hash get一下,如果不为空就不拚,为空就拚.
把目标有的字符的对应值设为1,如目标字符串为"io",i值为105,o为111,则把b[105],b[111]设为1.
然后在拚字符串前先把源串的那个字符对应的index值是否为1,为0则拚在上面,为1就不拚.这样比hash要快.