জাভা: শুরুতে sertোকানোর জন্য স্ট্রিংবিল্ডার ব্যবহার করুন


94

আমি কেবল স্ট্রিং দিয়ে এটি করতে পারি, উদাহরণস্বরূপ:

String str="";
for(int i=0;i<100;i++){
    str=i+str;
}

স্ট্রিংবিল্ডারের সাথে এটি অর্জন করার কোনও উপায় আছে কি? ধন্যবাদ

উত্তর:


189
StringBuilder sb = new StringBuilder();
for(int i=0;i<100;i++){
    sb.insert(0, Integer.toString(i));
}

সতর্কতা: এটি এর উদ্দেশ্যকে পরাস্ত করেStringBuilder , তবে আপনি যা চান তা তা করে।


আরও ভাল কৌশল (যদিও এখনও এটি আদর্শ নয়):

  1. আপনি string োকাতে চান প্রতিটি স্ট্রিং বিপরীত ।
  2. প্রতিটি স্ট্রিং এ এ যুক্ত করুনStringBuilder
  3. সম্পূর্ণ হয়ে StringBuilder গেলে সম্পূর্ণ বিপরীত করুন ।

এটি একটি ও ( এন ²) সমাধানকে ও ( এন ) এ পরিণত করবে।


4
... যেহেতু এটি AbstractStringBuilderসন্নিবেশ সূচকে সমস্ত সামগ্রী সন্নিবেশ করানো হয়েছে যাতে সন্নিবেশকৃতদের জন্য জায়গা খুঁজে পাওয়া যায়। যাইহোক, এটি একটি বাস্তবায়ন বিবরণ, নীতি এক নয়।
entonio

4
@ সেন্টোনিও: আসলে, তবে এটি একটি অত্যন্ত সমালোচনামূলক বিবরণ। :)
user541686

4
আমি দেখতে পাচ্ছি, দেখে মনে হচ্ছে আমার তখন স্ট্রিংবিল্ডার ব্যবহার করা উচিত নয়, অনেক অনেক ধন্যবাদ
ব্যবহারকারী 685275

@ ব্যবহারকারী 5৮৫২75৫: হ্যাঁ, যদি আপনার পিছনের সন্নিবেশ প্রয়োজন হয় তবে আপনার সত্যিকারের এমন কিছু দরকার যা স্ট্রিংয়ের শুরুতে সন্নিবেশ করতে পারে। আমি মনে করি সবচেয়ে সহজ সমাধানটি উপরের কৌশলটি (জিনিসগুলিকে দু'বার বিপরীত করা), যদিও আপনি সম্ভবত চর অ্যারে দিয়ে আপনার নিজের থেকে আরও ভাল বর্গ তৈরি করতে পারেন ("ডেক" এর দিকে নজর দিতে চান)।
user541686

4
@ আরগারডপ্যাক: আমি বলব এটি মেকানিজম, উদ্দেশ্য নয়। উদ্দেশ্যটি হ'ল স্ট্রিং ম্যানিপুলেশনের চেয়ে তাত্পর্যপূর্ণভাবে দ্রুত হওয়া, যা আপনি এটি ভুল ব্যবহার করলে তা হবে না।
ব্যবহারকারী541686


13

হতে পারে আমি কিছু মিস করছি তবে আপনি এমন একটি স্ট্রিং দিয়ে বাছাই করতে চান যা দেখতে এমন "999897969594...543210", সঠিক?

StringBuilder sb = new StringBuilder();
for(int i=99;i>=0;i--){
    sb.append(String.valueOf(i));
}

আশ্চর্যজনক এই পোস্টটি লুপের চতুর হেরফের দ্বারা সমাধান প্রদানের সময় খুব বেশি ভোট পেল না
নাম-সোম-

4
@ নাম-সোম-ইআর তিনি কেবল স্ট্রিংকে উল্টাচ্ছেন। এটি বাম দিকে সংযুক্ত করার উত্তর দেয় না।
রেমন্ড চেনন

পছন্দসই প্রভাব অর্জন করে।
স্পেক

আমি মনে করি যে এরকম ক্ষেত্রেও হতে পারে যে আপনি স্ট্রিংবিল্ডারের আসল সম্ভাবনাটি ব্যবহার করে শুরুতে সন্নিবেশ করানোর কোনও উপায় হ্যাক করার পরিবর্তে এই পদ্ধতির ব্যবহার করতে পারেন। যাইহোক, এমন কেস রয়েছে যেখানে আপনি লুপটি বিপরীত করতে পারবেন না যাতে আপনার অন্যান্য উত্তরও প্রয়োজন।
ফোনিক্স

7

বিকল্প সমাধান হিসাবে আপনি সমস্ত স্ট্রিং সংরক্ষণ করার জন্য একটি লাইফ স্ট্রাকচার (স্ট্যাকের মতো) ব্যবহার করতে পারেন এবং আপনার কাজ শেষ হয়ে গেলে এগুলি সমস্ত কিছু বাইরে নিয়ে স্ট্রিংবিল্ডারে রেখে দিন। এটি স্বাভাবিকভাবে এটিতে রাখা আইটেমগুলির (স্ট্রিং) ক্রমটিকে বিপরীত করে।

Stack<String> textStack = new Stack<String>();
// push the strings to the stack
while(!isReadingTextDone()) {
    String text = readText();
    textStack.push(text);
}
// pop the strings and add to the text builder
String builder = new StringBuilder(); 
while (!textStack.empty()) {
      builder.append(textStack.pop());
}
// get the final string
String finalText =  builder.toString();

4
ArrayDequeপরিবর্তে ব্যবহার করা উচিত Stack। "LIFO স্ট্যাক অপারেশনের আরও সম্পূর্ণ এবং সামঞ্জস্যপূর্ণ সেট {@ লিঙ্ক ডেক} ইন্টারফেস এবং এর বাস্তবায়ন দ্বারা সরবরাহ করা হয়েছে, যা এই শ্রেণীর পক্ষে অগ্রাধিকার হিসাবে ব্যবহার করা উচিত।"
লুনা

5

এই থ্রেডটি বেশ পুরানো তবে আপনি স্ট্রিংবিল্ডার পূরণের জন্য পুনরাবৃত্ত সমাধানের কথাও ভাবতে পারেন। এটি কোনও বিপরীত প্রক্রিয়াজাতকরণ ইত্যাদি রোধ করতে সহায়তা করে কেবল আপনার পুনরাবৃত্তির সাথে আপনার পুনরাবৃত্তির নকশা করা এবং সতর্কতার সাথে একটি প্রস্থান শর্তের জন্য সিদ্ধান্ত নেওয়া দরকার।

public class Test {

    public static void main(String[] args) {
        StringBuilder sb = new StringBuilder();
        doRecursive(sb, 100, 0);
        System.out.println(sb.toString());
    }

    public static void doRecursive(StringBuilder sb, int limit, int index) {
        if (index < limit) {
            doRecursive(sb, limit, index + 1);
            sb.append(Integer.toString(index));
        }
    }
}

3

আমি যখন এই পোস্টে হোঁচট খেয়েছি তখন আমারও একই রকম প্রয়োজন ছিল। আমি একটি স্ট্রিং তৈরির দ্রুত উপায় চেয়েছিলাম যা উভয় দিক থেকে বৃদ্ধি পেতে পারে। সামনে নতুন অক্ষর যুক্ত করুন পাশাপাশি নির্বিচারে ফিরে। আমি জানি এটি একটি পুরানো পোস্ট, তবে এটি স্ট্রিংগুলি তৈরির কয়েকটি উপায় চেষ্টা করতে আমাকে অনুপ্রাণিত করেছিল এবং আমি ভেবেছিলাম যে আমি আমার অনুসন্ধানগুলি ভাগ করব। আমি এটিতে কয়েকটি জাভা 8 কনস্ট্রাক্টও ব্যবহার করছি, যা 4 এবং 5 এর ক্ষেত্রে গতি অনুকূল করতে পারে।

https://gist.github.com/SidWagz/e41e836dec65ff24f78afdf8669e6420

উপরের গিস্টটিতে বিশদ কোড রয়েছে যা যে কেউ চালাতে পারে। আমি এর মধ্যে কয়েকটি বড় স্ট্রিং বাড়িয়েছি; ১) স্ট্রিংবিল্ডারে সংযোজন, ২) @ মেহরদাদ যেমনটি দেখিয়েছে স্ট্রিংবিল্ডারের সামনের দিকে sertোকান, ৩) স্ট্রিংবিল্ডারের সমাপ্তির পাশাপাশি আংশিকভাবে সন্নিবেশ করান, ৪) শেষ হতে সংযোজনের জন্য একটি তালিকা ব্যবহার করে, ৫) একটি ডিক ব্যবহার করে সামনে থেকে সংযোজন

// Case 2    
StringBuilder build3 = new StringBuilder();
IntStream.range(0, MAX_STR)
                    .sequential()
                    .forEach(i -> {
                        if (i%2 == 0) build3.append(Integer.toString(i)); else build3.insert(0, Integer.toString(i));
                    });
String build3Out = build3.toString();


//Case 5
Deque<String> deque = new ArrayDeque<>();
IntStream.range(0, MAX_STR)
                .sequential()
                .forEach(i -> {
                    if (i%2 == 0) deque.addLast(Integer.toString(i)); else deque.addFirst(Integer.toString(i));
                });

String dequeOut = deque.stream().collect(Collectors.joining(""));

আমি কেবলমাত্র মামলার সম্মুখভাগে নজর রাখব focus কেস 2 এবং কেস ৫। স্ট্রিংবিল্ডারের বাস্তবায়ন অভ্যন্তরীণভাবে সিদ্ধান্ত নেয় কীভাবে অভ্যন্তরীণ বাফারটি বৃদ্ধি পায়, যা সামনের অ্যাডেন্ডিংয়ের ক্ষেত্রে সমস্ত বাফারকে বামে ডানদিকে সরানো ছাড়াও। @ মেহেরদাড দ্বারা দেখানো স্ট্রিংবিল্ডারের সামনের দিকে সরাসরি whenোকানোর সময় নেওয়া সময়টি যখন নেওয়া হয় ঠিক তেমনই হয় তবে @ মেহেরদাড দেখিয়েছেন, যদি প্রয়োজনটি কেবল 90k অক্ষরের চেয়ে কম দৈর্ঘ্যের স্ট্রিংগুলির (যা এখনও অনেকটা) থাকে তবে সামনের সন্নিবেশ সন্নিবেশ করা হবে একই সাথে একটি স্ট্রিং তৈরি করুন ঠিক একই সময়ে যুক্ত করে একই দৈর্ঘ্যের একটি স্ট্রিং তৈরি করতে। আমি যা বলছি তা হ'ল সেই সময় পেনাল্টিটি সত্যই কিক করে এবং বিশাল হয়, তবে কেবল যখন আপনাকে সত্যিই বিশাল স্ট্রিং তৈরি করতে হয়। একজন উদাহরণস্বরূপ ব্যবহার করতে পারেন এবং আমার উদাহরণে দেখানো হয়েছে শেষে স্ট্রিংগুলিতে যোগ দিতে পারেন।

আসলে কেস 2 এর জন্য পারফরম্যান্স কেস 1 এর চেয়ে অনেক দ্রুত, যা আমি বুঝতে পারছি না। আমি ধরে নিচ্ছি স্ট্রিংবিল্ডারের অভ্যন্তরীণ বাফারটির জন্য সামনের সংযোজন এবং ব্যাক সংযোজন সম্পর্কিত ক্ষেত্রে একই হবে। আমি এমনকি গাদা বৃদ্ধিতে বিলম্ব এড়ানোর জন্য ন্যূনতম হিপকে একটি বৃহত পরিমাণে সেট করেছি, যদি এটি কোনও ভূমিকা পালন করে। হয়তো আরও ভাল বোঝার কেউ নীচে মন্তব্য করতে পারেন।


1
Difference Between String, StringBuilder And StringBuffer Classes
String
String is immutable ( once created can not be changed )object. The object created as a
String is stored in the Constant String Pool.
Every immutable object in Java is thread-safe, which implies String is also thread-safe. String
can not be used by two threads simultaneously.
String once assigned can not be changed.
StringBuffer
StringBuffer is mutable means one can change the value of the object. The object created
through StringBuffer is stored in the heap. StringBuffer has the same methods as the
StringBuilder , but each method in StringBuffer is synchronized that is StringBuffer is thread
safe .
Due to this, it does not allow two threads to simultaneously access the same method. Each
method can be accessed by one thread at a time.
But being thread-safe has disadvantages too as the performance of the StringBuffer hits due
to thread-safe property. Thus StringBuilder is faster than the StringBuffer when calling the
same methods of each class.
String Buffer can be converted to the string by using
toString() method.

    StringBuffer demo1 = new StringBuffer("Hello") ;

// The above object stored in heap and its value can be changed.
/
// Above statement is right as it modifies the value which is allowed in the StringBuffer
StringBuilder
StringBuilder is the same as the StringBuffer, that is it stores the object in heap and it can also
be modified. The main difference between the StringBuffer and StringBuilder is
that StringBuilder is also not thread-safe.
StringBuilder is fast as it is not thread-safe.
/
// The above object is stored in the heap and its value can be modified
/
// Above statement is right as it modifies the value which is allowed in the StringBuilder

4
স্ট্যাকওভারফ্লোতে স্বাগতম। কোডটি কী করে এবং কীভাবে এটি সমস্যার সমাধান করে তা একটি ব্যাখ্যা অন্তর্ভুক্ত করুন।
খারাপ_কোডার

1

আপনি অফসেট সহ সন্নিবেশ পদ্ধতিটি ব্যবহার করতে পারেন। '0' তে অফসেট সেট হওয়ার অর্থ আপনি আপনার স্ট্রিংবিল্ডারের সামনের দিকে সংযোজন করছেন।

StringBuilder sb = new StringBuilder();
for(int i=0;i<100;i++){
    sb.insert(0,i);
}

দ্রষ্টব্য : sertোকানোর পদ্ধতিটি সমস্ত প্রকারের আদিমিকে গ্রহণ করে, আপনি ইনট, দীর্ঘ, চর [] ইত্যাদির জন্য ব্যবহার করতে পারেন etc.


0

কেমন:

StringBuilder builder = new StringBuilder();
for(int i=99;i>=0;i--){
    builder.append(Integer.toString(i));
}
builder.toString();

বা

StringBuilder builder = new StringBuilder();
for(int i=0;i<100;i++){
  builder.insert(0, Integer.toString(i));
}
builder.toString();

তবে এটির সাহায্যে আপনি ও (এন) এর পরিবর্তে অপারেশন O (N ^ 2) করছেন।

জাভা ডক্স থেকে স্নিপেট:

এই অক্ষর অনুক্রমের মধ্যে অবজেক্ট আর্গুমেন্টের স্ট্রিং প্রতিনিধিত্ব সন্নিবেশ করানো হয়। সামগ্রিক প্রভাবটি হুবহু হ'ল দ্বিতীয় তর্কটিকে পদ্ধতি দ্বারা একটি স্ট্রিংয়ে রূপান্তরিত করা হয়েছিল String.valueOf(Object)এবং সেই স্ট্রিংয়ের অক্ষরগুলি নির্দেশিত অফসেটে এই অক্ষর অনুক্রমের মধ্যে প্রবেশ করানো হয়েছিল।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.