প্যারামিটারগুলি এবং মানগুলির ক্ষেত্রে মানগুলি বনাম


327

structগোতে এর মান বা স্লাইস ফেরত দেওয়ার বিভিন্ন উপায় রয়েছে । আমি পৃথক ব্যক্তিদের জন্য দেখেছি:

type MyStruct struct {
    Val int
}

func myfunc() MyStruct {
    return MyStruct{Val: 1}
}

func myfunc() *MyStruct {
    return &MyStruct{}
}

func myfunc(s *MyStruct) {
    s.Val = 1
}

আমি এইগুলির মধ্যে পার্থক্য বুঝতে পারি। প্রথমটি কাঠামোর একটি অনুলিপি প্রদান করে, দ্বিতীয়টি ফাংশনের মধ্যে তৈরি কাঠামোর মানটির জন্য একটি পয়েন্টার, তৃতীয়টি বিদ্যমান স্ট্রাক্টটি পাস করার এবং মানটিকে ওভাররাইড করার প্রত্যাশা করে।

আমি এই সমস্ত নিদর্শনগুলি বিভিন্ন প্রসঙ্গে ব্যবহার করতে দেখেছি, আমি ভাবছি যে এগুলি সম্পর্কে সর্বোত্তম অনুশীলনগুলি কী। আপনি কখন ব্যবহার করবেন? উদাহরণস্বরূপ, প্রথমটি ছোট স্ট্রাকগুলির জন্য ঠিক হতে পারে (কারণ ওভারহেডটি ন্যূনতম), বড়গুলির ক্ষেত্রে দ্বিতীয়। এবং তৃতীয়টি যদি আপনি চূড়ান্ত মেমরির দক্ষ হতে চান তবে আপনি কলগুলির মধ্যে সহজেই একটি একক কাঠামো পুনরায় ব্যবহার করতে পারেন। কোনটি কখন ব্যবহার করবেন তার জন্য কোনও সেরা অনুশীলন রয়েছে?

একইভাবে, টুকরা সংক্রান্ত একই প্রশ্ন:

func myfunc() []MyStruct {
    return []MyStruct{ MyStruct{Val: 1} }
}

func myfunc() []*MyStruct {
    return []MyStruct{ &MyStruct{Val: 1} }
}

func myfunc(s *[]MyStruct) {
    *s = []MyStruct{ MyStruct{Val: 1} }
}

func myfunc(s *[]*MyStruct) {
    *s = []MyStruct{ &MyStruct{Val: 1} }
}

আবার: এখানে সেরা অনুশীলনগুলি কি। আমি জানি টুকরো সবসময় পয়েন্টার হয়, সুতরাং একটি স্লাইসে পয়েন্টার ফেরানো কার্যকর নয়। তবে, আমি কি স্ট্রাক্ট মানগুলির একটি স্লাইস, স্ট্রাক্টের পয়েন্টারগুলির একটি স্লাইস ফিরিয়ে আনব, আমি কি পয়েন্টারটিতে একটি স্লাইসে আর্গুমেন্ট হিসাবে যেতে পারি ( গো অ্যাপ ইঞ্জিন এপিআইতে ব্যবহৃত প্যাটার্ন )?


1
আপনি যেমনটি বলেছেন, এটি সত্যই ব্যবহারের ক্ষেত্রে নির্ভর করে। পরিস্থিতির উপর নির্ভর করে সমস্ত বৈধ - এটি কি কোনও পরিবর্তনীয় বস্তু? আমরা কি একটি অনুলিপি বা পয়েন্টার চাই? ইত্যাদি বিটিডব্লিউ আপনি ব্যবহারের কথা উল্লেখ করেন নি new(MyStruct):) তবে পয়েন্টার বরাদ্দ এবং সেগুলি ফেরত দেওয়ার বিভিন্ন পদ্ধতির মধ্যে আসলেই কোনও পার্থক্য নেই।
নয়_এ_গল্ফার

15
আক্ষরিক অর্থে ইঞ্জিনিয়ারিং। স্ট্রাক্টগুলি অবশ্যই বেশ বড় হতে হবে যে কোনও পয়েন্টার ফিরিয়ে দেওয়া আপনার প্রোগ্রামটিকে আরও দ্রুত করে তোলে। শুধু বিরক্ত করবেন না, কোড, প্রোফাইল, কার্যকর হলে ঠিক করুন।
ভোলকার 13

1
মান বা পয়েন্টার ফিরিয়ে দেওয়ার একমাত্র উপায় আছে এবং তা হ'ল মান বা পয়েন্টারটি ফেরত দেওয়া। আপনি কীভাবে তাদের বরাদ্দ করেন তা একটি পৃথক সমস্যা issue আপনার পরিস্থিতির জন্য কী কাজ করে তা ব্যবহার করুন এবং আপনার চিন্তার আগে কিছু কোড লিখুন।
জিমবি

3
বিটিডাব্লু কৌতূহলের বাইরে আমি এটিকে বেঁধে দিয়েছি। স্ট্রাইক বনাম বনাম পয়েন্টারগুলি মোটামুটি একই গতি বলে মনে হয় তবে পয়েন্টারগুলি লাইনগুলিতে ফাংশনগুলিতে প্রেরণ করা গুরুতরভাবে দ্রুত হয়। যদিও একটি স্তরে না হলেও এটি
বিবেচ্য

1
@ নট_এ_গল্ফার: আমি ধরে নেব যে কেবলমাত্র বিসি বরাদ্দ ফাংশনের বাইরে করা হয়েছে। পয়েন্টার বনাম মানদণ্ডগুলি সত্যের পরে স্ট্রাক্ট এবং মেমরি অ্যাক্সেসের ধরণগুলির আকারের উপর নির্ভর করে। ক্যাশে-লাইন আকারের জিনিসগুলি অনুলিপি করা আপনি যত তাড়াতাড়ি পেতে পারেন এবং সিপিইউ ক্যাশে থেকে ডিফারেন্সিং পয়েন্টারগুলির গতি প্রধান মেমরি থেকে সেগুলি ডিফারেন্স করার চেয়ে অনেক আলাদা।
জিমবি

উত্তর:


392

tl; dr :

  • রিসিভার পয়েন্টার ব্যবহার করার পদ্ধতিগুলি সাধারণ; গ্রহীতার জন্য থাম্বের নিয়মটি হল , "যদি সন্দেহ হয় তবে একটি পয়েন্টার ব্যবহার করুন।"
  • স্লাইস, মানচিত্র, চ্যানেল, স্ট্রিং, ফাংশন মান এবং ইন্টারফেস মানগুলি অভ্যন্তরীণভাবে পয়েন্টারগুলির সাথে প্রয়োগ করা হয় এবং এগুলিতে একটি পয়েন্টার প্রায়শই অনর্থক হয়।
  • অন্য কোথাও, আপনাকে বড় স্ট্রাক বা স্ট্রাইকগুলির জন্য পয়েন্টার ব্যবহার করুন এবং অন্যথায় মানগুলি পাস করুন , কারণ পয়েন্টারের মাধ্যমে আশ্চর্য হয়ে জিনিসগুলি পরিবর্তন করা বিভ্রান্তিকর।

একটি ক্ষেত্রে যেখানে আপনার প্রায়শই পয়েন্টার ব্যবহার করা উচিত:

  • রিসিভারগুলি অন্যান্য আর্গুমেন্টগুলির চেয়ে প্রায়শই পয়েন্টার হয়। পদ্ধতির পক্ষে তারা যে জিনিসটি আহ্বান করেছে তা সংশোধন করার জন্য, বা নামযুক্ত প্রকারকে বড় বড় স্ট্রাক হিসাবে চিহ্নিত করা অস্বাভাবিক নয়, সুতরাং বিরল ক্ষেত্রে বাদে নির্দেশিকা পয়েন্টারে ডিফল্ট হয়ে যায় to
    • জেফ হজসের কপিফাইটার সরঞ্জামটি স্বয়ংক্রিয়ভাবে মান দ্বারা পাস করা ক্ষুদ্র-ক্ষুদ্র রিসিভারের জন্য অনুসন্ধান করে।

কিছু পরিস্থিতি যেখানে আপনার পয়েন্টার প্রয়োজন নেই:

  • কোড পর্যালোচনা নির্দেশাবলী যেমন ছোট স্ট্রাকগুলি পাস করার পরামর্শ দেয়type Point struct { latitude, longitude float64 } , এবং মানগুলি হিসাবে কিছুটা বড় হতে পারে তেমন প্রস্তাব দেয় যদি না আপনি যে ফাংশনটিতে কল করছেন সেখানে সেগুলি সংশোধন করতে সক্ষম হওয়া প্রয়োজন।

    • মান শব্দার্থবিজ্ঞানগুলি এলিয়জিং পরিস্থিতিগুলি এড়ায় যেখানে এখানে একটি অ্যাসাইনমেন্ট সেখানে অবাক করে দিয়ে সেখানে একটি মান পরিবর্তন করে।
    • সামান্য গতির জন্য পরিষ্কার শব্দার্থক বলিদান করা গো-ওয়াই নয়, এবং কখনও কখনও মূল্য দ্বারা ছোট স্ট্রাকগুলি পাস করা আসলে আরও কার্যকর, কারণ এটি ক্যাশে মিস করা এড়ায় because বা হিপ বরাদ্দ এড়ায়।
    • সুতরাং, যান উইকির কোড পর্যালোচনা মন্তব্য পৃষ্ঠাতে যখন স্ট্রাক্টগুলি ছোট হয় এবং সম্ভবত সেভাবেই থাকার সম্ভাবনা থাকে তখন মান দিয়ে চলে যাওয়ার পরামর্শ দেয়।
    • যদি "বৃহত" কাটঅফটি অস্পষ্ট মনে হয় তবে তা হয়; যুক্তিযুক্তভাবে অনেক স্ট্রাক্ট এমন একটি পরিসরে থাকে যেখানে পয়েন্টার বা মান ঠিক হয়। নিম্ন সীমা হিসাবে, কোড পর্যালোচনা মন্তব্যগুলি স্লাইসগুলি (তিনটি মেশিন শব্দ) মান রিসিভার হিসাবে ব্যবহার করার পক্ষে যুক্তিযুক্ত বলে মনে করে। উপরের বাউন্ডের কাছাকাছি কিছু হিসাবে, bytes.Replace10 টি শব্দের মূল্যবান আরগস (তিনটি স্লাইস এবং একটি int) লাগে ।
  • জন্য টুকরা , আপনি অ্যারের পরিবর্তন উপাদান একটি পয়েন্টার পাস প্রয়োজন হবে না। উদাহরণস্বরূপ, io.Reader.Read(p []byte)এর বাইট পরিবর্তন করে p। এটা তর্কসাপেক্ষ একটি বিশেষ ক্ষেত্রে "মান মত আচরণ সামান্য structs মধ্যে," অভ্যন্তরীণভাবে আপনি একটু গঠন একটি নামক প্রায় পার করছি যেহেতু ফালি হেডার (দেখুন Russ কক্সবাজার (RSC) 'র ব্যাখ্যা )। একইভাবে, কোনও মানচিত্র সংশোধন করতে বা কোনও চ্যানেলে যোগাযোগ করার জন্য আপনাকে পয়েন্টার লাগবে না ।

  • জন্য টুকরা আপনি reslice করব (এর শুরু / দৈর্ঘ্য / ধারণক্ষমতা পরিবর্তন), বিল্ট-ইন ফাংশন পছন্দ appendএকটি ফালি মান গ্রহণ এবং একটি নতুন ফিরে যান। আমি তা অনুকরণ করব; এটি এলিয়াসিং এড়ায়, একটি নতুন স্লাইস ফিরিয়ে দেওয়া একটি নতুন অ্যারে বরাদ্দ হতে পারে এই দিকে দৃষ্টি আকর্ষণ করতে সহায়তা করে এবং এটি কলকারীদের কাছে পরিচিত।

    • এটি সর্বদা ব্যবহারিক নয় that ডাটাবেস ইন্টারফেস বা সিরিয়ালাইজারের মতো কিছু সরঞ্জাম এমন একটি টুকরোতে সংযোজন করা প্রয়োজন যার টাইপটি সংকলন সময়ে জানা যায় না। তারা কখনও কখনও interface{}প্যারামিটারে একটি স্লাইসে পয়েন্টার গ্রহণ করে ।
  • স্লাইসগুলির মতো মানচিত্র, চ্যানেল, স্ট্রিং এবং ফাংশন এবং ইন্টারফেস মানগুলি ইতিমধ্যে অভ্যন্তরীণ রেফারেন্স বা কাঠামো যা ইতিমধ্যে রেফারেন্স ধারণ করে, তাই যদি আপনি কেবল অন্তর্নিহিত ডেটা অনুলিপি করা এড়াতে চাইছেন তবে আপনাকে সেগুলিতে পয়েন্টার দেওয়ার দরকার নেই । (আরএসসি কীভাবে ইন্টারফেসের মানগুলি সংরক্ষণ করা হয় সে সম্পর্কে একটি পৃথক পোস্ট লিখেছিল )।

    • কলারের স্ট্রাক্টটি আপনি সংশোধন করতে চান এমন বিরল ক্ষেত্রে আপনাকে এখনও পয়েন্টারগুলি পাস করতে হতে পারে : উদাহরণস্বরূপ, সে কারণে এটি flag.StringVarগ্রহণ করে *string

আপনি যেখানে পয়েন্টার ব্যবহার করেন:

  • আপনার ফাংশনটি যে কোনও কাঠামোর জন্য আপনাকে পয়েন্টার লাগাতে হবে তা পদ্ধতি হওয়া উচিত কিনা তা বিবেচনা করুন। লোকেরা xপরিবর্তনের জন্য প্রচুর পদ্ধতি প্রত্যাশা করে x, তাই পরিবর্তিত কাঠামোটি রিসিভারটি তৈরি করে আশ্চর্য হ্রাস করতে সহায়তা করতে পারে। কখন গ্রহণকারীদের পয়েন্টার হওয়া উচিত সে সম্পর্কে গাইডলাইন রয়েছে।

  • তাদের অ-রিসিভার প্যারামগুলিতে যে ক্রিয়াকলাপগুলির প্রভাব রয়েছে সেগুলি গডোক বা আরও ভাল, গডোক এবং নাম (যেমন reader.WriteTo(writer)) তে পরিষ্কার করা উচিত।

  • আপনি পুনরায় ব্যবহারের অনুমতি দিয়ে বরাদ্দ এড়াতে একটি পয়েন্টার গ্রহণ করার কথা উল্লেখ করেছেন; মেমরি পুনঃব্যবহারের জন্য এপিআইগুলি পরিবর্তন করা একটি অপ্টিমাইজেশন হ'ল এটি বরাদ্দ না হওয়া পর্যন্ত আমি বিলম্ব করি, এবং এরপরে আমি এমন কোনও উপায় খুঁজব যা সমস্ত ব্যবহারকারীর উপর ট্রিলিয়ার এপিআই চাপায় না:

    1. বরাদ্দ এড়ানোর জন্য, গো এর পালানোর বিশ্লেষণটি আপনার বন্ধু। আপনি মাঝে মাঝে এটিকে তুচ্ছ নির্মাণকারী, একটি সরল আক্ষরিক, বা একটি দরকারী শূন্য মানের মতো শুরু করে এমন ধরণের তৈরি করে গাদা বরাদ্দ এড়াতে সহায়তা করতে পারেন bytes.Buffer
    2. Reset()কোনও স্টাডলিব টাইপের অফারের মতো কোনও জিনিসকে ফাঁকা অবস্থায় রেখে দেওয়ার জন্য একটি পদ্ধতি বিবেচনা করুন । যে ব্যবহারকারীরা কোনও বরাদ্দ যত্ন করে না বা সংরক্ষণ করতে পারে না তাদের কল করতে হবে না।
    3. সুবিধার্থে-স্থান-সংক্রান্ত পদ্ধতিগুলি লেখার বিষয়ে বিবেচনা করুন এবং মেলবন্ধ হিসাবে জোড়া হিসাবে স্ক্র্যাচ ফাংশন তৈরি করুন: existingUser.LoadFromJSON(json []byte) errorএগুলি মোড়ানো হতে পারে NewUserFromJSON(json []byte) (*User, error)। আবার, এটি পৃথক কলারের কাছে আলস্যতা এবং পিনিং বরাদ্দের মধ্যে পছন্দকে চাপ দেয়।
    4. মেমরি পুনর্ব্যবহার করতে চাইছেন কলকারীরা sync.Poolকিছু বিশদ পরিচালনা করতে পারেন । কোনও নির্দিষ্ট বরাদ্দ যদি প্রচুর মেমরি চাপ তৈরি করে, আপনি যখন নিশ্চিত হন যে আপনি বরাদ্দটি আর ব্যবহার করা হয় না তখন আপনি নিশ্চিত হন এবং আপনার আরও ভাল অপ্টিমাইজেশন উপলব্ধ নেই, sync.Poolসাহায্য করতে পারে। (ক্লাউডফ্লেয়ার পুনর্ব্যবহার সম্পর্কে একটি দরকারী (প্রাক sync.Pool) ব্লগ পোস্ট প্রকাশিত ।)

অবশেষে, আপনার স্লাইসগুলি পয়েন্টারগুলির মধ্যে হওয়া উচিত কিনা: মানগুলির স্লাইসগুলি কার্যকর হতে পারে এবং আপনার বরাদ্দ এবং ক্যাশে মিস করে সংরক্ষণ করে। ব্লকার থাকতে পারে:

  • আপনার আইটেমগুলি তৈরি করার জন্য এআইপিআই আপনাকে পয়েন্টারগুলিকে জোর করতে পারে, যেমন আপনাকে শূন্য মানেরNewFoo() *Foo সাথে আরম্ভ করার পরিবর্তে কল করতে হবে ।
  • আইটেমগুলির কাঙ্ক্ষিত লাইফটাইমগুলি সব একই হতে পারে। পুরো টুকরো একবারে মুক্তি দেওয়া হয়; যদি আইটেমগুলির 99% আর কার্যকর না হয় তবে আপনার অন্য 1% পয়েন্টার রয়েছে তবে অ্যারের সমস্ত বরাদ্দ থাকবে।
  • আইটেমগুলির চারপাশে সরানো আপনার সমস্যার কারণ হতে পারে। উল্লেখযোগ্যভাবে, appendআইটেমগুলি অনুলিপি করে যখন এটি অন্তর্নিহিত অ্যারে বৃদ্ধি করে । আপনি পয়েন্টারগুলির appendপরে ভুল জায়গায় পয়েন্টার আগে পেয়েছিলেন , অনুলিপি বড় স্ট্রাকগুলির জন্য ধীর হতে পারে এবং উদাহরণস্বরূপ sync.Mutexঅনুলিপি অনুমোদিত নয়। মাঝখানে সন্নিবেশ / মুছুন এবং একইভাবে আইটেমগুলি প্রায় সরান।

আপনি যদি আপনার সমস্ত আইটেম সামনের দিকে রাখেন এবং সেগুলি স্থানান্তরিত না করেন তবে (উদাহরণস্বরূপ, appendপ্রাথমিক সেটআপের পরে আর কোনও এস) না রাখলে, বা যদি আপনি এগুলির চারপাশে সরানো চালিয়ে যান তবে আপনি অবশ্যই নিশ্চিত হন যে মান স্লাইসগুলি বোঝায় that's ঠিক আছে (আইটেমগুলিতে পয়েন্টার ব্যবহারের / সাবধানে ব্যবহারের প্রয়োজন নেই, আইটেমগুলি দক্ষতার সাথে অনুলিপি করার জন্য যথেষ্ট ছোট ইত্যাদি)। কখনও কখনও আপনাকে নিজের অবস্থার সুনির্দিষ্ট বৈশিষ্ট্যগুলি সম্পর্কে ভাবতে বা পরিমাপ করতে হয় তবে এটি একটি রুক্ষ গাইড।


12
বড় স্ট্রাইক মানে কি? একটি বড় কাঠামো এবং একটি ছোট কাঠামোর উদাহরণ আছে?
ব্যবহারকারী

1
কীভাবে আপনি বাইটগুলি বলতে পারেন? প্রতিস্থাপনে amd64 এ 80 বাইটের মূল্যবান আরগস লাগে?
টিম উ

2
স্বাক্ষরটি হ'ল Replace(s, old, new []byte, n int) []byte; s, পুরাতন এবং নতুন প্রতিটি তিনটি শব্দ ( স্লাইস শিরোনামগুলি হয়(ptr, len, cap) ) এবং n intএটি একটি শব্দ, সুতরাং 10 শব্দ, যা আট বাইট / শব্দে 80 বাইট হয়।
twotwotwo

6
আপনি কীভাবে বড় স্ট্রাইক সংজ্ঞায়িত করেন? বড় কত বড়?
অ্যান্ডি

3
@ অ্যান্ডি অ্যাল্ডো আমার উত্সগুলির কোনও (কোড পর্যালোচনা মন্তব্যসমূহ ইত্যাদি) একটি প্রান্তিক সংজ্ঞা দেয় না, তাই আমি সিদ্ধান্ত নিলাম যে এটি একটি প্রান্তিকতা না বাড়িয়ে বিচারের আহ্বান জানিয়েছে। তিনটি শব্দ (একটি স্লাইসের মতো) স্ট্যান্ডলিবের মান হিসাবে যোগ্য হিসাবে বিবেচনা করা হয় consistent আমি এখনই একটি পাঁচ-শব্দের মান রিসিভারের একটি উদাহরণ পেয়েছি (পাঠ্য / স্ক্যানার P পজিশন) তবে আমি এটিতে খুব বেশি পড়তে পারি না (এটি পয়েন্টার হিসাবেও পাস হয়েছে!)। অনুপস্থিত বেঞ্চমার্ক, ইত্যাদি, আমি কেবল পাঠযোগ্যতার পক্ষে সবচেয়ে সুবিধাজনক বলে মনে করতাম।
twotwotwo

10

তিনটি প্রধান কারণ যখন আপনি পয়েন্টার হিসাবে পদ্ধতি রিসিভারগুলি ব্যবহার করতে চান:

  1. "প্রথম এবং সবচেয়ে গুরুত্বপূর্ণ, পদ্ধতিটির কি রিসিভারটি সংশোধন করা দরকার? যদি তা হয় তবে গ্রহীতা অবশ্যই পয়েন্টার হতে হবে।"

  2. "দ্বিতীয়টি হ'ল দক্ষতার বিবেচনা। যদি রিসিভারটি বড় হয়, উদাহরণস্বরূপ একটি বড় কাঠামো, এটি পয়েন্টার রিসিভার ব্যবহার করা অনেক সস্তা হবে" "

  3. "এরপরে ধারাবাহিকতা রয়েছে the ধরণের কিছু পদ্ধতির অবশ্যই পয়েন্টার রিসিভার থাকতে হবে, বাকিগুলিও হওয়া উচিত, সুতরাং পদ্ধতি সেটটি কীভাবে ব্যবহৃত হয় নির্বিশেষে সামঞ্জস্যপূর্ণ"

তথ্যসূত্র: https://golang.org/doc/faq# ম্যাসিডস_অন_ভ্যালু_অর_পয়েন্টার

সম্পাদনা: আর একটি গুরুত্বপূর্ণ বিষয় আপনি প্রকৃত "প্রকার" যা আপনি ফাংশনে পাঠাচ্ছেন তা জানা to প্রকারটি হয় 'মান প্রকার' বা 'রেফারেন্স টাইপ' হতে পারে।

এমনকি স্লাইস এবং মানচিত্রগুলি রেফারেন্স হিসাবে কাজ করে, আমরা ফাংশনে স্লাইসের দৈর্ঘ্য পরিবর্তন করার মতো পরিস্থিতিতে পয়েন্টার হিসাবে তাদের পাস করতে চাই।


1
2 এর জন্য, কাট অফ কি? আমার স্ট্রাক্ট বড় বা ছোট কিনা আমি কীভাবে জানব? এছাড়াও, এমন একটি কাঠামো কি এত ছোট যে পয়েন্টারের চেয়ে মানটি ব্যবহার করা আরও দক্ষ (যাতে এটি গাদা থেকে রেফারেন্স করতে না হয়)?
zlotnika

আমি ভিতরে ক্ষেত্র এবং / বা নেস্টেড স্ট্রাইকগুলির সংখ্যা যত বেশি বলব স্ট্রাক্টটি তত বেশি। আমি নিশ্চিত নই যে কোনও কাঠামোকে কখন "বড়" বা "বৃহত্তর" বলা যেতে পারে তা জানার নির্দিষ্ট নির্দিষ্ট কাটঅফ বা মানক উপায় রয়েছে কিনা। যদি আমি কোনও স্ট্রাক্ট ব্যবহার করি বা তৈরি করি তবে আমি জানতে পারব যে এটি উপরে বা উপরে আমি যা বলেছি তার উপর ভিত্তি করে ছোট। তবে এটাই আমি!
সন্তোষ পিল্লাই

2

যদি আপনি (উদাহরণস্বরূপ একটি অ-ভাগ করা সংস্থান যা রেফারেন্স হিসাবে পাস করার প্রয়োজন হয় না) করতে পারেন তবে একটি মান ব্যবহার করুন। নিম্নলিখিত কারণে:

  1. আপনার কোডটি আরও ভাল এবং আরও পঠনযোগ্য হবে, পয়েন্টার অপারেটর এবং নাল চেক এড়ানো হবে।
  2. নাল পয়েন্টার আতঙ্কের বিরুদ্ধে আপনার কোডটি নিরাপদ হবে।
  3. আপনার কোডটি প্রায়শই দ্রুত হবে: হ্যাঁ, দ্রুত! কেন?

কারণ 1 : আপনি স্ট্যাকের মধ্যে কম আইটেম বরাদ্দ করবেন। স্ট্যাক থেকে বরাদ্দ / ডিলোকেটিং তাত্ক্ষণিক, তবে গাদাতে বরাদ্দ / বিলম্বকরণ খুব ব্যয়বহুল হতে পারে (বরাদ্দ সময় + আবর্জনা সংগ্রহ)। আপনি এখানে কিছু প্রাথমিক সংখ্যা দেখতে পারেন: http://www.macias.info/entry/201802102230_go_values_vs_references.md

কারণ 2 : বিশেষত যদি আপনি ফালিগুলিতে ফিরে আসা মানগুলি সঞ্চয় করেন তবে আপনার মেমরির বস্তুগুলি মেমরিতে আরও কমপ্যাক্ট হবে: যেখানে সমস্ত আইটেম মেমরির অন্যান্য অংশের দিকে নির্দেশ করে সেখানে একটি স্লাইসটি পুনরায় তৈরি করার চেয়ে আরও দ্রুত হয় যেখানে সমস্ত আইটেম সংমিশ্রিত হয় a । ইন্ডিরিয়েশন পদক্ষেপের জন্য নয় তবে ক্যাশে মিস করা বৃদ্ধির জন্য।

পৌরাণিক বিভাজক : একটি সাধারণ x86 ক্যাশে লাইন 64৪ বাইট। বেশিরভাগ স্ট্রাক্ট এর চেয়ে ছোট। মেমোরিতে ক্যাশে লাইনটি অনুলিপি করার সময়টি একটি পয়েন্টার অনুলিপি করার অনুরূপ।

কেবলমাত্র আপনার কোডের একটি সমালোচনামূলক অংশ যদি ধীর হয় তবে আমি কিছু মাইক্রো-অপ্টিমাইজেশান চেষ্টা করব এবং পয়েন্টার ব্যবহার করে কিছুটা কম পঠনযোগ্যতা এবং ম্যানটেইনেবিলিটি ব্যয়ে কিছুটা গতি উন্নত করে কিনা তা পরীক্ষা করে দেখব।


1

একটি ক্ষেত্রে যেখানে আপনি সাধারণত একটি পয়েন্টার ফেরত প্রয়োজন একটি নির্মাণ করছে উদাহরণস্বরূপ কিছু stateful বা ভাগ করে নেওয়ার যোগ্য সম্পদ । এটি প্রায়শই উপসর্গযুক্ত ফাংশন দ্বারা করা হয়New

যেহেতু তারা কোনও কিছুর একটি নির্দিষ্ট উদাহরণ উপস্থাপন করে এবং তাদের কিছু ক্রিয়াকলাপের সমন্বয় সাধনের প্রয়োজন হতে পারে, একই উত্সকে উপস্থাপন করে নকল / অনুলিপি কাঠামো উত্পন্ন করার পক্ষে এটি প্রচুর অর্থবোধ করে না - সুতরাং প্রত্যাবর্তিত পয়েন্টারটি উত্সটিতে নিজেই হ্যান্ডেল হিসাবে কাজ করে ।

কিছু উদাহরণ:

অন্যান্য ক্ষেত্রে, পয়েন্টারগুলি কেবল ফিরে আসে কারণ ডিফল্টরূপে কাঠামোটি অনুলিপি করতে খুব বড় হতে পারে:


বিকল্পভাবে, অভ্যন্তরীণভাবে পয়েন্টার রয়েছে এমন কোনও কাঠামোর অনুলিপি ফেরানোর মাধ্যমে সরাসরি পয়েন্টারগুলি এড়ানো সম্ভব নয়, তবে সম্ভবত এটি অহংকার হিসাবে বিবেচিত হয় না:


এই বিশ্লেষণে অন্তর্ভুক্তটি হ'ল, ডিফল্টরূপে স্ট্রোকগুলি মান দ্বারা অনুলিপি করা হয় (তবে প্রয়োজনীয়ভাবে তাদের নির্দেশিত সদস্যদের নয়)।
21
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.