MutableState — Compose में प्रेक्षणीय अवस्था और अद्यतन तंत्र

लेखक: IT Sectr प्रकाशित: 2026-06-28 पढ़ने का समय: 7 मिनट

MutableState Jetpack Compose में एक इंटरफ़ेस है जो एक परिवर्तनीय प्रेक्षणीय मान के लिए कंटेनर का प्रतिनिधित्व करता है। यह Compose की प्रतिक्रियात्मक प्रणाली का आधार है: जब भी MutableState का मान setter के माध्यम से बदलता है, Compose Runtime सभी पढ़ने वाले घटकों को सूचित करता है और पुनंराम्बन चलाता है। Google Android Developers, 2026 के अनुसार, एक घोषणात्मक UI में अवस्था के साथ सही ढंग से काम करने के लिए MutableState को समझना अनिवार्य है।

मुख्य बातें

  • MutableState — compose.runtime इंटरफ़ेस जिसमें एक ही value प्रॉपर्टी है (getter + setter)
  • State — केवल पढ़ने के लिए मूल इंटरफ़ेस, MutableState लिखने की क्षमता जोड़ता है
  • पुनंराम्बन एक सक्रिय snapshot चक्र के भीतर value का setter बुलाने पर चलता है
  • SnapshotMutationPolicy यह निर्धारित करता है कि पुनंराम्बन के लिए परिवर्तन कब महत्वपूर्ण माना जाता है
  • MutableIntState और समान — MutableState के ऑप्टिमाइज्ड प्राइमिटिव संस्करण

Jetpack Compose में MutableState क्या है

MutableState androidx.compose.runtime पैकेज का एक इंटरफ़ेस है जो एक ही प्रॉपर्टी घोषित करता है: override var value: T। getter मौजूदा मान लौटाता है, setter नया मान लिखता है और Compose Runtime को परिवर्तन की सूचना देता है। यह इंटरफ़ेस State<T> से विरासत पाता है, जहाँ value केवल पढ़ने के लिए है। यह दो-स्तरीय आर्किटेक्चर अभिगम को अलग करने की अनुमति देता है: एक घटक जो केवल मान पढ़ना चाहता है, उसे State<T> मिलता है, जबकि स्वामी घटक को MutableState<T> मिलता है।

MutableState का डिफ़ॉल्ट कार्यान्वयन आंतरिक क्लास SnapshotMutableStateImpl है, जो परिवर्तनों को ट्रैक करने के लिए snapshot तंत्र का उपयोग करता है। जब value का setter बुलाया जाता है, तो वर्तमान snapshot लेखन को रिकॉर्ड करता है और सभी पंजीकृत ObservedScope को अमान्य के रूप में चिह्नित करता है। ये दायरे (आमतौर पर Composable फ़ंक्शन्स) अगले फ़्रेम पर पुनंरम्बित होंगे। Lock-free snapshot आर्किटेक्चर के कारण पूरी प्रक्रिया सिंक्रोनियरूप से और बिना लॉक के होती है।

State vs MutableState: State एक केवल पढ़ने के लिए इंटरफ़ेस है जो सार्वजनिक घटक API के लिए उपयोग होता है। जब आप एक Composable फ़ंक्शन पैरामीटर को State<Int> के रूप में घोषित करते हैं, तो आप गारंटी देते हैं कि घटक अवस्था को पढ़ सकता है लेकिन बदल नहीं सकता। MutableState का उपयोग स्वामी घटक के अंदर किया जाता है। यह पृथक्करण Compose की बुनियादी प्रथाओं में से एक है जो अनएलॉभराइज़्ड परिवर्तनों को रोकता है।

State, MutableState और व्युत्पन्न इंटरफ़ेस का पदक्रम

Compose में अवस्था इंटरफ़ेस का पदक्रम कई स्तरों का है। सबसे ऊपर State<T> है जिसमें केवल पढ़ने के लिए value है। नीचे MutableState<T> है जिसमें पढ़ने-लिखने के लिए value है। इसके बाद विशेषिकृत प्राइमिटिव संस्करण आते हैं: MutableIntState, MutableFloatState, MutableLongState, MutableBooleanState और अन्य, जो प्राइमिटिव को बॉक्सिंग से बचाते हैं।

MutableDoubleState और MutableLongState कम सामान्य हैं लेकिन मौजूद हैं। संग्रह इंटरफ़ेस: MutableListState — सूची के अंदर परिवर्तनों को ट्रैक करने के लिए, MutableStateMap — मैप के लिए। इनमें से प्रत्येक इंटरफ़ेस एक विशिष्ट परिदृश्य के लिए ऑप्टिमाइज़्ड है और अतिरिक्त संग्रह हेरफेर विधियों के साथ मूल MutableState को बढ़ाता है।

SnapshotStateList और SnapshotStateMap snapshots के साथ संगत परिवर्तनीय सूचियों और मैप के कार्यान्वयन हैं। वे न केवल मान प्रतिस्थापन बल्कि आंतरिक परिवर्तनों को भी ट्रैक कर सकते हैं: सूची में आईटम जोड़ना, हटाना, मौजूदा आईटम बदलना। इन संरचनाओं के लिए, mutableStateListOf() और mutableStateMapOf() संगत प्रेक्षणीय संग्रह बनाते हैं।

इंटरफ़ेसउद्देश्यनिर्माण विधि
State<T>केवल पढ़ने के लिए कंटेनर
MutableState<T>पढ़ने-लिखने के लिए कंटेनरmutableStateOf()
MutableIntStateबॉक्सिंग के बिना प्राइमिटिव IntmutableIntStateOf()
MutableFloatStateबॉक्सिंग के बिना प्राइमिटिव FloatmutableFloatStateOf()
SnapshotStateListप्रेक्षणीय सूचीmutableStateListOf()
SnapshotStateMapप्रेक्षणीय मैपmutableStateMapOf()

SnapshotMutationPolicy: पुनंराम्बन कब चलाना है

SnapshotMutationPolicy एक इंटरफ़ेस है जो यह निर्धारित करता है कि MutableState में परिवर्तन कब महत्वपूर्ण माना जाता है। mutableStateOf दूसरे तर्क के रूप में policy स्वीकार करता है। मानक कार्यान्वयन: structuralEquality() (equals), referentialEquality() (===), neverEqualPolicy() (हमेशा परिवर्तन को मानता है)। कस्टम तर्क के लिए अपनी नीति लागू की जा सकती है।

structuralEquality() — डिफ़ॉल्ट व्यवहार। Compose नए मान की तुलना पुराने से equals() के माध्यम से करता है। यदि परिणाम true है, तो पुनंराम्बन नहीं चलता। यह प्राइमिटिव्स और data classes के लिए सुविधाजनक है, जहां समान क्षेत्रों वाले दो उदाहरण समान माने जाते हैं। समस्या: यदि data class में List है, तो equals() गहराई से तुलना करता है, जो बड़ी सूचियों के लिए महंगा हो सकता है।

referentialEquality() — === के माध्यम से संदर्भों की तुलना करता है। पुनंराम्बन केवल तब ही चलता है जब एक अलग ऑब्जेक्ट निर्दिष्ट किया जाता है, भले ही सामग्री समान हो। यह अपरिवर्तनीय data classes के लिए इष्टतम है जहां प्रत्येक नया उदाहरण परिवर्तन की गारंटी देता है। neverEqualPolicy() — तुलना किए बिना हमेशा परिवर्तन को महत्वपूर्ण मानता है। तब उपयोगी जब setter शायद ही बुलाया जाता है और equals पर समय खर्च करने की आवश्यकता नहीं है।

kotlin
    // Policy comparison in practice
data class User(val name: String, val age: Int)

@Composable
fun UserProfile() {
    // structuralEquality: recomposition ONLY if data changed
    var user1 by remember {
        mutableStateOf(User("Alice", 30))
    }

    // referentialEquality: recomposition on ANY assignment
    var user2 by remember {
        mutableStateOf(User("Bob", 25),
            SnapshotMutationPolicy.referentialEquality())
    }

    // user1: copy() with same fields does NOT trigger recomposition
    // user2: even user2.copy() == user2 triggers recomposition (new ref)
}

प्राइमिटिव State: MutableIntState, MutableFloatState, MutableLongState

प्राइमिटिव MutableIntState और समान विशेषिकृत इंटरफ़ेस हैं जो बॉक्सिंग के बिना प्राइमिटिव्स को संग्रहीत करते हैं। एक सामान्य MutableState<Int> Int को Integer के रूप में संग्रहीत करता है, जो प्रत्येक लेखन पर हीप पर एक ऑब्जेक्ट बनाता है। MutableIntState int (प्राइमिटिव) को संग्रहीत करता है, जो बॉक्सिंग के ऑवरहेड को पूर्णतः समाप्त करता है। यह उच्च-आवृत्ति अद्यतनों के लिए विशेष रूप से महत्वपूर्ण है — काउंटर, स्क्रॉल स्थिति, एनिमेशन मान।

mutableIntStateOf(), mutableFloatStateOf(), mutableLongStateOf() — फ़ंक्शन्स जो प्राइमिटिव MutableState बनाते हैं। इंटरफ़ेस को MutableIntState, MutableFloatState, MutableLongState कहा जाता है। वे क्रमशः MutableState<Int>, MutableState<Float> और MutableState<Long> का विस्तार करते हैं, तेज़ प्राइमिटिव पहुंच के लिए intValue प्रॉपर्टी जोड़ते हैं। उनके आंतरिक कार्यान्वयन में लॉक-मुक्त पढ़ने/लिखने के लिए AtomicInteger का उपयोग होता है।

उपयोग: काउंटर (Int), स्क्रॉल स्थिति (Float offset), समय टैंट (Long)। अधिकांश रोजमर्रा के परिदृश्यों में प्रदर्शन अंतर ध्यान देने योग्य नहीं है, लेकिन हजारों आईटम्स और संक्रमण एनिमेशन के साथ LazyList में, प्राइमिटिव State एक महत्वपूर्ण बूस्ट प्रदान करता है। Google सार्वभौमिक mutableStateOf के बजाय विशिष्ट परिदृश्यों के लिए प्राइमिटिव State का उपयोग करने की अनुशंसा देता है।

kotlin
@Composable
fun ScrollCounter() {
    // Bad: boxing on every update
    var badCount by remember { mutableStateOf(0) }

    // Good: no boxing, primitive storage
    var goodCount by remember { mutableIntStateOf(0) }

    // Usage is identical
    Button(onClick = { goodCount++ }) {
        Text("Count: $goodCount")
    }
}

MutableState के साथ काम करने के व्यावहारिक उदाहरण

एक TodoList घटक पर विचार करें, जहाँ MutableState का उपयोग दो रूपों में होता है: इनपुट अवस्था के लिए अलग-अलग चार और एक गतिशील कार्य सूची के लिए SnapshotStateList के रूप में। दोनों कोड की संक्षिप्तता के लिए प्रतिनिधित्व का उपयोग करते हैं।

kotlin
data class TodoItem(val id: Int, val text: String, val isDone: Boolean = false)

@Composable
fun TodoScreen() {
    var inputText by remember { mutableStateOf("") }
    val items = remember { mutableStateListOf() }

    Column(modifier = Modifier.padding(16.dp)) {
        Row {
            TextField(
                value = inputText,
                onValueChange = { inputText = it }
            )
            Button(onClick = {
                if (inputText.isNotBlank()) {
                    items.add(TodoItem(items.size, inputText))
                    inputText = ""
                }
            }) { Text("Add") }
        }

        LazyColumn {
            items(items) { item ->
                Row(modifier = Modifier.fillMaxWidth().clickable {
                    val idx = items.indexOf(item)
                    items[idx] = item.copy(isDone = !item.isDone)
                }) {
                    Checkbox(checked = item.isDone, onCheckedChange = null)
                    Text(item.text)
                }
            }
        }
    }
}

mutableStateListOf एक SnapshotStateList बनाता है — एक परिवर्तनीय सूची जो अलग-अलग तत्वों में परिवर्तनों को ट्रैक करती है। जब items.add() और items[n] = newValue का उपयोग किया जाता है, Compose मुटेशन को देखता है और केवल LazyColumn के उन तत्वों को पुनंरम्बित करता है जो बदल गए। inputText एक सामान्य MutableState<String> है। दो MutableState प्रकारों (एकल और संग्रह) का संयोजन फ़ॉर्म और सूचियों वाली स्क्रीनों के लिए एक विशिष्ट पैटर्न है।

अक्सर पूछे जाने वाले प्रश्न

क्या मैं MutableState का उपयोग remember के बिना कर सकता हूँ?

MutableState बिना remember के प्रत्येक पुनंराम्बन पर नया बनेगा। mutableStateOf का प्रत्येक नया कॉल एक नया ऑब्जेक्ट बनाता है, और पुराना मान खो जाता है। State को पुनंराम्बनों के बीच संरक्षित रखने के लिए हमेशा remember का उपयोग करें, जब तक कि State Composable के बाहर नहीं बनाया गया है (जैसे ViewModel में)।

MutableState को एक सामान्य चार में कैसे बदलें?

.value को snapshot { } के माध्यम से snapshot के बाहर एक बार पढ़ें। लेकिन यह प्रतिक्रियाशीलता को निष्क्रिय कर देता है — परिवर्तन अब पुनंराम्बन को चलाने का कारण नहीं बनेंगे। बिना सदस्यता के एकबार पढ़ने के लिए, बिना पढ़े snapshot के अंदर currentValue() का उपयोग करें।

कौन तेज़ है: mutableStateOf या mutableIntStateOf?

mutableIntStateOf तेज़ है क्योंकि इसे int को Integer में बॉक्स करने की आवश्यकता नहीं है। प्रति सेकंड हजारों अद्यतनों (एनिमेशन, स्क्रॉलिंग) के साथ, आवंटन समय में अंतर 30-50% तक पहुँच सकता है। दुर्लभ अद्यतनों (क्लिक्स, टेक्स्ट इनपुट) के लिए, अंतर नगण्य है।

क्या MutableState का उपयोग Composable फ़ंक्शन तर्क के रूप में किया जा सकता है?

हाँ, लेकिन अनुशंसित नहीं है। MutableState के बजाय, State (केवल पढ़ने के लिए) + onValueChange लैंब्डा पास करें। यह State Hoisting पैटर्न को लागू करता है और घटक को पुनःप्रयोज्य बनाता है। MutableState स्वीकार करने वाले घटक एकदिशीय डेटा प्रवाह का उल्लंघन करते हैं।

कस्टम MutableState कार्यान्वयन कैसे बनाएं?

MutableState इंटरफ़ेस को लागू करें और getter और setter के साथ override var value प्रदान करें। setter में आप मान्यता या लॉगिंग जोड़ सकते हैं। Compose Runtime के साथ पीछे की अनुकूलता के लिए, अपने कस्टम कार्यान्वयन को snapshotFlow में लपेटें या snapshotIncrement का उपयोग करें।

सारांश

  • MutableState — Compose में परिवर्तनीय प्रेक्षणीय अवस्था के लिए मूल इंटरफ़ेस
  • State — बिना परिवर्तन अधिकार के डेटा पास करने के लिए केवल पढ़ने का संस्करण
  • SnapshotMutationPolicy परिवर्तन पर पुनंराम्बन चलाने की शर्तों का प्रबंधन करता है
  • प्राइमिटिव State (MutableIntState और अन्य) बॉक्सिंग ओवरहेड को समाप्त करते हैं
  • SnapshotStateList और SnapshotStateMap संग्रहों के आंतरिक परिवर्तनों को ट्रैक करते हैं
  • पुनंराम्बन value के setter को किसी भी कॉल पर स्वचालित रूप से शुरू होता है
  • अनुशंसा: अवस्था के स्वामित्व के लिए MutableState और नीचे भेजने के लिए State का उपयोग करें

हम एक मोबाइल एप्लिकेशन टर्नकी विकसित करेंगे

IT Sectr 2017 से स्टार्टअप और व्यवसायों के लिए iOS और Android एप्लिकेशन बनाता है। हम आपको सलाह देंगे और सर्वोत्तम समाधान प्रस्तावित करेंगे।

परियोजना पर चर्चा करें

यह भी पढ़ें