পাইথনের অন্য ফাংশনে আর্গুমেন্ট সহ ফাংশনগুলি পাস করছেন?


203

পাইথনের অন্য ফাংশনে যুক্তি সহ ফাংশনগুলি পাস করা কি সম্ভব?

এর মতো কিছু বলুন:

def perform(function):
    return function()

তবে যে ফাংশনগুলি পাস করতে হবে তার মধ্যে এই জাতীয় যুক্তি থাকবে:

action1()
action2(p)
action3(p,r)

উত্তর:


289

আপনি এই মানে?

def perform( fun, *args ):
    fun( *args )

def action1( args ):
    something

def action2( args ):
    something

perform( action1 )
perform( action2, p )
perform( action3, p, r )

10
নামকরণ পরামিতি সম্পর্কে কি? এটি হ'ল, def action1(arg1, arg2=None, arg3=None)উদাহরণস্বরূপ, আপনি কীভাবে একটি আর্গুমেন্টটি পাস করতে পারেন যা আপনি arg3 এ অর্পণ করতে চান?
চেমকুট

6
(মজা, ** args) কার্য সম্পাদন, দেখতে stackoverflow.com/questions/8954746/...
Mannaggia

কি হবে যদি performএবং action1, action2বিভিন্ন ফাইল? @ S.Lott
Alper

@ আল্পার সেগুলি আমদানি করুন
pfabri

122

লাম্বদা এটির জন্য:

def Perform(f):
    f()

Perform(lambda: Action1())
Perform(lambda: Action2(p))
Perform(lambda: Action3(p, r))

7
কৌতূহলের বাইরেও, আপনি দয়া করে আমাকে বলতে পারেন কেন লাম্বডাস এই ক্ষেত্রে ভাল নয়?
জোয়ান ওয়েঙ্গ

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

3
আমি দেখতে পাই যে সীমিত বাক্য গঠন প্রায় অস্বচ্ছ; তারা n00bz ব্যাখ্যা করা কঠিন। হ্যাঁ, তারা এখানে কাজ করে এবং সিনট্যাক্সের বিভ্রান্তিকর বৈশিষ্ট্য অনুপস্থিত। এটি হ'ল - সম্ভবত - আমি ল্যাম্বডা দেখেছি এমন একমাত্র উদাহরণ যা অস্পষ্ট নয়।
এস .লট

11
যাতে আপনি পাস করা ফাংশনটির ফলাফলটি পুনরুদ্ধার করতে পারফর্ম () "সুনির্দিষ্টভাবে কল (एफ)) না দিয়ে" রিটার্ন এফ () "বললে ভাল হয় না।
মুহাককে

আমি মনে করি যে ল্যাম্বডা সংস্করণটি বেশ ঝরঝরে, কিন্তু অদ্ভুতভাবে পরীক্ষাগুলিতে আমি দৌড়েছি যে ল্যাম্বদার মাধ্যমে ফাংশনগুলি কল করা আরও উত্তরে আলোচিত fn (* আরগস) পদ্ধতির চেয়ে ধীর ছিল।
রিচার্ড শেফার্ড

39

আপনি যেমন ফান্টুলগুলি থেকে আংশিক ফাংশনটি ব্যবহার করতে পারেন।

from functools import partial

def perform(f):
    f()

perform(Action1)
perform(partial(Action2, p))
perform(partial(Action3, p, r))

কীওয়ার্ড সহও কাজ করে

perform(partial(Action4, param1=p))

1
functools.partialperformআরও পরামিতিগুলির হস্তান্তর করার প্রয়োজন হলে এটি আরও বহুমুখী f। যেমন, কেউ কল করতে পারে perform(partial(Action3, p))এবং এর perform(f)মতো কিছু করতে পারে f("this is parameter r")
রবার্ট

13

ল্যাংডাস নয়, ফান্টাকুলস.পার্পিয়াল ব্যবহার করুন! এবং অফ পারফর্ম একটি অকেজো ফাংশন, আপনি সরাসরি ফাংশনগুলির চারপাশে যেতে পারেন।

for func in [Action1, partial(Action2, p), partial(Action3, p, r)]:
  func()


3
পারফর্মের কল সাইটে আপনি যুক্তিগুলি মূল্যায়ন করতে চান কিনা তা নির্ভর করে।
ডেভ

6

(মাস পরে) একটি ছোট্ট বাস্তব উদাহরণ যেখানে ল্যাম্বডা দরকারী, আংশিক নয়:
বলুন যে আপনি একটি 2-মাত্রিক ক্রিয়াকলাপের মাধ্যমে বিভিন্ন 1-মাত্রিক ক্রস-বিভাগ চান, যেমন পাহাড়ের সারি দিয়ে কাটা টুকরা।
quadf( x, f )একটি 1-ডি লাগে fএবং বিভিন্ন জন্য এটি কল x
Y = -1 0 1 এ উল্লম্ব কাট এবং x = -1 0 1 এ অনুভূমিক কাটগুলির জন্য এটি কল করতে,

fx1 = quadf( x, lambda x: f( x, 1 ))
fx0 = quadf( x, lambda x: f( x, 0 ))
fx_1 = quadf( x, lambda x: f( x, -1 ))
fxy = parabola( y, fx_1, fx0, fx1 )

f_1y = quadf( y, lambda y: f( -1, y ))
f0y = quadf( y, lambda y: f( 0, y ))
f1y = quadf( y, lambda y: f( 1, y ))
fyx = parabola( x, f_1y, f0y, f1y )

আমি যতদূর জানি, এটি partialকরতে পারবেন না -

quadf( y, partial( f, x=1 ))
TypeError: f() got multiple values for keyword argument 'x'

(কীভাবে এইগুলিতে ফাঁকা, আংশিক, ল্যাম্বদা ট্যাগ যুক্ত করবেন?)


5

এটিকে আংশিক ফাংশন বলা হয় এবং এটি করার কমপক্ষে 3 টি উপায় রয়েছে। আমার প্রিয় উপায়ে ল্যাম্বদা ব্যবহার করা হচ্ছে কারণ এটি অতিরিক্ত প্যাকেজের উপর নির্ভরতা এড়ায় এবং সর্বনিম্ন ভার্বোজ। ধরুন আপনার কোনও ফাংশন রয়েছে add(x, y)এবং আপনি add(3, y)প্যারামিটার হিসাবে অন্য কোনও ফাংশনে পাস করতে চান যাতে অন্য ফাংশনটির মান স্থির করে y

ল্যাম্বদা ব্যবহার করুন

# generic function takes op and its argument
def runOp(op, val):
    return op(val)

# declare full function
def add(x, y):
    return x+y

# run example
def main():
    f = lambda y: add(3, y)
    result = runOp(f, 1) # is 4

নিজের র‍্যাপার তৈরি করুন

এখানে আপনাকে একটি ফাংশন তৈরি করতে হবে যা আংশিক ফাংশনটি ফিরিয়ে দেয়। এটি স্পষ্টতই অনেক বেশি ভার্বোস।

# generic function takes op and its argument
def runOp(op, val):
    return op(val)

# declare full function
def add(x, y):
    return x+y

# declare partial function
def addPartial(x):
    def _wrapper(y):
        return add(x, y)
    return _wrapper

# run example
def main():
    f = addPartial(3)
    result = runOp(f, 1) # is 4

ফান্টুলগুলি থেকে আংশিক ব্যবহার করুন

এটি lambdaউপরে দেখানো প্রায় অভিন্ন । তাহলে আমাদের কেন এটি দরকার? এর কয়েকটি কারণ রয়েছে । সংক্ষেপে, partialকিছু ক্ষেত্রে কিছুটা দ্রুত হতে পারে (এর বাস্তবায়ন দেখুন ) এবং আপনি এটি লম্বা দেরীতে দেরী করার জন্য প্রারম্ভিক বাঁধাইয়ের জন্য ব্যবহার করতে পারেন।

from functools import partial

# generic function takes op and its argument
def runOp(op, val):
    return op(val)

# declare full function
def add(x, y):
    return x+y

# run example
def main():
    f = partial(add, 3)
    result = runOp(f, 1) # is 4

1

বন্ধ করার সাথে এটি করার একটি উপায় এখানে:

    def generate_add_mult_func(func):
        def function_generator(x):
            return reduce(func,range(1,x))
        return function_generator

    def add(x,y):
        return x+y

    def mult(x,y):
        return x*y

    adding=generate_add_mult_func(add)
    multiplying=generate_add_mult_func(mult)

    print adding(10)
    print multiplying(10)

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