sort
প্যাকেজ:
type Interface interface {
Len() int
Less(i, j int) bool
Swap(i, j int)
}
...
type reverse struct {
Interface
}
Interface
কাঠামোয় বেনামে ইন্টারফেসের অর্থ কী reverse
?
sort
প্যাকেজ:
type Interface interface {
Len() int
Less(i, j int) bool
Swap(i, j int)
}
...
type reverse struct {
Interface
}
Interface
কাঠামোয় বেনামে ইন্টারফেসের অর্থ কী reverse
?
উত্তর:
এই পদ্ধতিতে বিপরীত প্রয়োগ করে sort.Interface
এবং আমরা অন্য সমস্তকে সংজ্ঞায়িত না করেই একটি নির্দিষ্ট পদ্ধতিকে ওভাররাইড করতে পারি
type reverse struct {
// This embedded Interface permits Reverse to use the methods of
// another Interface implementation.
Interface
}
লক্ষ্য করুন এখানে কীভাবে এটি (j,i)
পরিবর্তে পরিবর্তিত হয় (i,j)
এবং বাস্তবায়নের reverse
পরেও এটি স্ট্রাক্টের জন্য ঘোষিত একমাত্র পদ্ধতিreverse
sort.Interface
// Less returns the opposite of the embedded implementation's Less method.
func (r reverse) Less(i, j int) bool {
return r.Interface.Less(j, i)
}
এই পদ্ধতির ভিতরে যেই স্ট্রাক্ট পাস করা হয় আমরা এটিকে নতুন reverse
স্ট্রাক্টে রূপান্তর করি ।
// Reverse returns the reverse order for data.
func Reverse(data Interface) Interface {
return &reverse{data}
}
আসল মানটি আসে যদি আপনি যদি ভাবেন যে এই পদ্ধতির পক্ষে সম্ভব না হয় তবে আপনাকে কী করতে হবে।
Reverse
পদ্ধতি যুক্ত sort.Interface
?এই যে কোনও পরিবর্তনের জন্য হাজার হাজার প্যাকেজগুলিতে কোডের আরও অনেক লাইন প্রয়োজন হবে যা স্ট্যান্ডার্ড বিপরীত কার্যকারিতাটি ব্যবহার করতে চায়।
reverse
টি সদস্য ধরনের Interface
। এর পরে এই সদস্যটির বহিরাগত কাঠামোয় বা অরাইড্রয়েডে এর পদ্ধতিগুলি কলযোগ্য।
extend
নন-অ্যাবস্ট্রাক্ট সাব-ক্লাস বাড়ানোর জন্য? আমার কাছে, অভ্যন্তরীণ দ্বারা প্রয়োগ করা বিদ্যমানগুলি ব্যবহার করার সময় কেবলমাত্র কয়েকটি নির্দিষ্ট পদ্ধতিকে ওভাররাইড করার এটি একটি সহজ উপায় হতে পারে Interface
।
return r.Interface.Less(j, i)
অভিভাবক বাস্তবায়ন কল করছে?
sort.Sort(sort.Reverse(sort.IntSlice(example)))
। আমার জন্য এখানে ব্যথার বিন্দু: পদ্ধতিটি বাছাই বিপরীত কাঠামোতে প্রচারিত হয়, তবে কলটি অ-সদস্য (রিসিভার) স্টাইল।
ঠিক আছে, গৃহীত উত্তরটি আমাকে বুঝতে সাহায্য করেছে, তবে আমি এমন একটি ব্যাখ্যা পোস্ট করার সিদ্ধান্ত নিয়েছি যা আমি মনে করি আমার চিন্তাভাবনার চেয়ে ভাল।
"কার্যকরী যান" এমবেডেড অন্যান্য ইন্টারফেসগুলি থাকার ইন্টারফেসগুলি উদাহরণ রয়েছে:
// ReadWriter is the interface that combines the Reader and Writer interfaces.
type ReadWriter interface {
Reader
Writer
}
এবং অন্যান্য কাঠামো এম্বেড থাকা একটি কাঠামো:
// ReadWriter stores pointers to a Reader and a Writer.
// It implements io.ReadWriter.
type ReadWriter struct {
*Reader // *bufio.Reader
*Writer // *bufio.Writer
}
তবে কোনও ইন্টারফেস এম্বেড করা স্ট্রাক্টের উল্লেখ নেই। এটি sort
প্যাকেজে দেখে আমি বিভ্রান্ত হয়ে পড়েছিলাম :
type Interface interface {
Len() int
Less(i, j int) bool
Swap(i, j int)
}
...
type reverse struct {
Interface
}
তবে ধারণাটি সহজ। এটি প্রায় একই:
type reverse struct {
IntSlice // IntSlice struct attaches the methods of Interface to []int, sorting in increasing order
}
IntSlice
উন্নীত করার পদ্ধতিগুলি reverse
।
এবং এই:
type reverse struct {
Interface
}
এর অর্থ এটি sort.reverse
ইন্টারফেস প্রয়োগ করে এমন কোনও কাঠামো এম্বেড করতে পারে sort.Interface
এবং ইন্টারফেসের যে কোনও পদ্ধতি রয়েছে, সেগুলিতে উন্নীত হবে reverse
।
sort.Interface
এমন পদ্ধতি রয়েছে Less(i, j int) bool
যা এখন ওভাররাইড করা যেতে পারে:
// Less returns the opposite of the embedded implementation's Less method.
func (r reverse) Less(i, j int) bool {
return r.Interface.Less(j, i)
}
বোঝার ক্ষেত্রে আমার বিভ্রান্তি
type reverse struct {
Interface
}
এটাই আমি ভেবেছিলাম যে কোনও স্ট্রাক্টের সর্বদা স্থির কাঠামো থাকে, অর্থাত্ নির্দিষ্ট ধরণের ক্ষেত্রগুলির নির্দিষ্ট সংখ্যা।
তবে নিম্নলিখিতগুলি আমাকে ভুল প্রমাণ করেছে:
package main
import "fmt"
// some interface
type Stringer interface {
String() string
}
// a struct that implements Stringer interface
type Struct1 struct {
field1 string
}
func (s Struct1) String() string {
return s.field1
}
// another struct that implements Stringer interface, but has a different set of fields
type Struct2 struct {
field1 []string
dummy bool
}
func (s Struct2) String() string {
return fmt.Sprintf("%v, %v", s.field1, s.dummy)
}
// container that can embedd any struct which implements Stringer interface
type StringerContainer struct {
Stringer
}
func main() {
// the following prints: This is Struct1
fmt.Println(StringerContainer{Struct1{"This is Struct1"}})
// the following prints: [This is Struct1], true
fmt.Println(StringerContainer{Struct2{[]string{"This", "is", "Struct1"}, true}})
// the following does not compile:
// cannot use "This is a type that does not implement Stringer" (type string)
// as type Stringer in field value:
// string does not implement Stringer (missing String method)
fmt.Println(StringerContainer{"This is a type that does not implement Stringer"})
}
বিবৃতি
type reverse struct {
Interface
}
reverse
ইন্টারফেস প্রয়োগ করে এমন প্রতিটি কিছু দিয়ে আপনাকে আরম্ভ করতে সক্ষম করে Interface
। উদাহরণ:
&reverse{sort.Intslice([]int{1,2,3})}
এইভাবে, এমবেড করা Interface
মান দ্বারা প্রয়োগ করা সমস্ত পদ্ধতি বাইরের দিকে পপুলেটে যায় যখন আপনি এখনও কিছুটিকে ওভাররাইড করতে সক্ষম হন reverse
, উদাহরণস্বরূপ Less
বাছাইয়ের বিপরীতে।
এই আসলে ঘটে যখন আপনি ব্যবহার করেন sort.Reverse
। আপনি অনুমানের স্ট্রাক্ট বিভাগে এম্বেডিং সম্পর্কে পড়তে পারেন ।
sort.Sort(sort.Reverse(sort.IntSlice(example)))
। আমার জন্য এখানে ব্যথার বিন্দু: পদ্ধতিটি বাছাই বিপরীত কাঠামোতে প্রচারিত হয়, তবে কলটি অ-সদস্য (রিসিভার) স্টাইল।
আমি আমার ব্যাখ্যাও দেব। sort
প্যাকেজ একটি unexported টাইপ সংজ্ঞায়িত reverse
, যা একটি struct, যে এম্বেড হয় Interface
।
type reverse struct {
// This embedded Interface permits Reverse to use the methods of
// another Interface implementation.
Interface
}
এটি অন্য ইন্টারফেস প্রয়োগের পদ্ধতিগুলি ব্যবহার করতে বিপরীতকে অনুমতি দেয়। এটি তথাকথিতcomposition
যা গোয়ের একটি শক্তিশালী বৈশিষ্ট্য।
Less
জন্য পদ্ধতি reverse
কল Less
এমবেডেড পদ্ধতি Interface
মান, কিন্তু সূচকের সঙ্গে ফ্লিপ সাজানোর ফলাফল ক্রম reversing।
// Less returns the opposite of the embedded implementation's Less method.
func (r reverse) Less(i, j int) bool {
return r.Interface.Less(j, i)
}
Len
এবং Swap
অন্যান্য দুটি পদ্ধতি reverse
, স্পষ্টভাবে মূল Interface
মান দ্বারা সরবরাহ করা হয় কারণ এটি একটি এমবেডেড ক্ষেত্র। রপ্তানি Reverse
ফাংশনের একটি দৃষ্টান্ত ফেরৎ reverse
যে ধরনের মূল রয়েছে Interface
মান।
// Reverse returns the reverse order for data.
func Reverse(data Interface) Interface {
return &reverse{data}
}
Less
জন্য পদ্ধতি reverse
কল Less
এমবেডেড পদ্ধতি Interface
মান, কিন্তু সূচকের ফ্লিপ সঙ্গে, সাজানোর ফলাফল ক্রম reversing।" - এটি পিতামাতার বাস্তবায়নের কলিংয়ের মতো দেখায়।
আমি এই বৈশিষ্ট্যটি খুব সহায়ক যখন লেখা খুঁজে নিয়ে মশকরা মধ্যে পরীক্ষার ।
এখানে যেমন একটি উদাহরণ:
package main_test
import (
"fmt"
"testing"
)
// Item represents the entity retrieved from the store
// It's not relevant in this example
type Item struct {
First, Last string
}
// Store abstracts the DB store
type Store interface {
Create(string, string) (*Item, error)
GetByID(string) (*Item, error)
Update(*Item) error
HealthCheck() error
Close() error
}
// this is a mock implementing Store interface
type storeMock struct {
Store
// healthy is false by default
healthy bool
}
// HealthCheck is mocked function
func (s *storeMock) HealthCheck() error {
if !s.healthy {
return fmt.Errorf("mock error")
}
return nil
}
// IsHealthy is the tested function
func IsHealthy(s Store) bool {
return s.HealthCheck() == nil
}
func TestIsHealthy(t *testing.T) {
mock := &storeMock{}
if IsHealthy(mock) {
t.Errorf("IsHealthy should return false")
}
mock = &storeMock{healthy: true}
if !IsHealthy(mock) {
t.Errorf("IsHealthy should return true")
}
}
ব্যবহার করে:
type storeMock struct {
Store
...
}
একজনকে সমস্ত Store
পদ্ধতি উপহাস করার দরকার নেই । শুধুমাত্র HealthCheck
উপহাস করা যায়, যেহেতু TestIsHealthy
পরীক্ষায় কেবল এই পদ্ধতিটি ব্যবহৃত হয় ।
test
আদেশের ফলাফলের নীচে :
$ go test -run '^TestIsHealthy$' ./main_test.go
ok command-line-arguments 0.003s
এডাব্লুএস এসডিকে পরীক্ষা করার সময় এই ব্যবহারের কেসটির একটি আসল বিশ্ব উদাহরণ খুঁজে পেতে পারে ।
এটিকে আরও সুস্পষ্ট করার জন্য, এখানে কুরুচিপূর্ণ বিকল্প রয়েছে - Store
ইন্টারফেসটি সন্তুষ্ট করার জন্য সর্বনিম্ন একটিকে প্রয়োগ করা দরকার :
type storeMock struct {
healthy bool
}
func (s *storeMock) Create(a, b string) (i *Item, err error) {
return
}
func (s *storeMock) GetByID(a string) (i *Item, err error) {
return
}
func (s *storeMock) Update(i *Item) (err error) {
return
}
// HealthCheck is mocked function
func (s *storeMock) HealthCheck() error {
if !s.healthy {
return fmt.Errorf("mock error")
}
return nil
}
func (s *storeMock) Close() (err error) {
return
}