আমি জানতে চাই কেন এই ফাংশন কাজ করে চান জাভা এবং kotlin সঙ্গে tailrec
কিন্তু নেই kotlin ছাড়া tailrec
?
সংক্ষিপ্ত উত্তর হ'ল আপনার কোটলিন পদ্ধতি JAVA এর চেয়ে "ভারী" । প্রতিটি কল এ এটি অন্য পদ্ধতিতে কল করে যা "উস্কানি দেয়" StackOverflowError
। সুতরাং, নীচে আরও বিস্তারিত ব্যাখ্যা দেখুন।
জাভা বাইটকোড সমতুল্য reverseString()
আমি আপনার পদ্ধতিগুলির জন্য বাইট কোডটি কোটলিন এবং জাভাতে যথাযথভাবে পরীক্ষা করে দেখেছি :
JAVA এ কোটলিন পদ্ধতি বাইটকোড
...
public final void reverseString(@NotNull char[] s) {
Intrinsics.checkParameterIsNotNull(s, "s");
this.helper(0, ArraysKt.getLastIndex(s), s);
}
public final void helper(int i, int j, @NotNull char[] s) {
Intrinsics.checkParameterIsNotNull(s, "s");
if (i < j) {
char t = s[j];
s[j] = s[i];
s[i] = t;
this.helper(i + 1, j - 1, s);
}
}
...
জাভা পদ্ধতিতে বাইকোড জাভা
...
public void reverseString(char[] s) {
this.helper(s, 0, s.length - 1);
}
public void helper(char[] s, int left, int right) {
if (left < right) {
char temp = s[left];
s[left++] = s[right];
s[right--] = temp;
this.helper(left, right, s);
}
}
...
সুতরাং, এখানে 2 প্রধান পার্থক্য রয়েছে:
Intrinsics.checkParameterIsNotNull(s, "s")
প্রত্যেকের জন্য প্রার্থনা করা হয় helper()
মধ্যে Kotlin সংস্করণ।
- জাভা পদ্ধতিতে বাম এবং ডান সূচকগুলি বর্ধিত হয়, কোটলিনে প্রতিটি পুনরাবৃত্তির জন্য নতুন সূচক তৈরি করা হয়।
সুতরাং, আসুন পরীক্ষা করা যাক কীভাবে Intrinsics.checkParameterIsNotNull(s, "s")
একা আচরণকে প্রভাবিত করে।
উভয় বাস্তবায়ন পরীক্ষা করুন
আমি উভয় ক্ষেত্রেই একটি সহজ পরীক্ষা তৈরি করেছি:
@Test
public void testJavaImplementation() {
char[] chars = new char[20000];
new Example().reverseString(chars);
}
এবং
@Test
fun testKotlinImplementation() {
val chars = CharArray(20000)
Example().reverseString(chars)
}
জন্য জাভা পরীক্ষা সমস্যা ছাড়াই সফল কিছুদিনের জন্য Kotlin এটি একটি কারণে miserably ব্যর্থ হয়েছে StackOverflowError
। তবে, আমি জাভা পদ্ধতিতে যুক্ত Intrinsics.checkParameterIsNotNull(s, "s")
করার পরে এটিও ব্যর্থ হয়েছিল:
public void helper(char[] s, int left, int right) {
Intrinsics.checkParameterIsNotNull(s, "s"); // add the same call here
if (left >= right) return;
char tmp = s[left];
s[left] = s[right];
s[right] = tmp;
helper(s, left + 1, right - 1);
}
উপসংহার
আপনার কোটলিন পদ্ধতির একটি ছোট পুনরাবৃত্তির গভীরতা রয়েছে কারণ এটি Intrinsics.checkParameterIsNotNull(s, "s")
প্রতিটি পদক্ষেপে আহ্বান জানায় এবং এটি তার জাভা সমমনা অংশের চেয়ে ভারী । আপনি যদি এই স্বয়ংক্রিয়ভাবে উত্পন্ন পদ্ধতিটি না চান তবে এখানে উত্তর হিসাবে সংকলনের সময় নাল চেকগুলি অক্ষম করতে পারেন
তবে, যেহেতু আপনি বুঝতে পেরেছেন কী উপকারটি tailrec
নিয়ে আসে (আপনার পুনরাবৃত্ত কলকে পুনরাবৃত্ত একটিতে রূপান্তর করে) আপনার সেই ব্যবহারটি করা উচিত।
tailrec
বা পুনরাবৃত্তি এড়ানো; উপলব্ধ স্ট্যাকের আকার রান, জেভিএম এবং সেট-আপগুলির মধ্যে এবং পদ্ধতি এবং তার প্যারামগুলির উপর নির্ভর করে পরিবর্তিত হয়। তবে যদি আপনি খাঁটি কৌতূহল জিজ্ঞাসা করে থাকেন (পুরোপুরি ভাল কারণ!) তবে আমি নিশ্চিত নই। আপনি সম্ভবত বাইকোড তাকান প্রয়োজন।