如何将变量传递到React Native的Alert.alert按钮的onPress方法中?
原因分析
- 这个问题本质是异步闭包陷阱:Alert的onPress回调是异步执行的,只有用户点击按钮的时候才会触发,此时外层的
item变量可能已经被后续代码修改、或者因为作用域问题已经被销毁/重置了。最常见的触发场景是你这段代码写在map/for循环内,且item是用var关键字声明的,var没有块级作用域,等回调触发时循环已经执行完毕,item已经是最终的undefined值。
解决方案
方案1:改用块级作用域声明变量(最推荐)
如果你的item是在循环中生成的,把声明item的关键字从var替换为const/let,这两个关键字支持块级作用域,每次循环都会生成独立的变量绑定,回调能正确捕获当前循环的item值:
// 示例循环写法,把var item改成let item即可 for(let i = 0; i < list.length; i++) { let item = list[i] // 用let/const声明,每个循环的item是独立的 console.log("HERE ITEM SHOWS THE CORRECT VALUES", item); Alert.alert( "Warning", "Test message", [ { text: "Cancel", onPress: () => console.log("Cancel Pressed"), style: "cancel" }, { text: "Start", onPress: () => { console.log("-----> 现在可以正常拿到item", item); } } ] ); }
方案2:用立即执行函数(IIFE)保存变量快照
如果不方便修改变量声明,可以用IIFE把当前的item值封存,回调会捕获IIFE参数里的静态值:
console.log("HERE ITEM SHOWS THE CORRECT VALUES", item); // 把Alert包裹在IIFE里,传入当前item作为参数 ((currentItem) => { Alert.alert( "Warning", "Test message", [ { text: "Cancel", onPress: () => console.log("Cancel Pressed"), style: "cancel" }, { text: "Start", onPress: () => { console.log("-----> 现在可以正常拿到item", currentItem); } } ] ); })(item) // 把当前的item传进去
方案3:用bind绑定参数
也可以通过Function.prototype.bind把item预先绑定为回调的参数:
console.log("HERE ITEM SHOWS THE CORRECT VALUES", item); Alert.alert( "Warning", "Test message", [ { text: "Cancel", onPress: () => console.log("Cancel Pressed"), style: "cancel" }, { text: "Start", onPress: ((currentItem) => { console.log("-----> 现在可以正常拿到item", currentItem); }).bind(this, item) // 把当前item绑定为回调的第一个参数 } ] );
内容的提问来源于stack exchange,提问作者she hates me
相关产品推荐
相关产品推荐

