【问题标题】:object not returning value in javascript对象在javascript中没有返回值
【发布时间】:2019-04-02 07:17:46
【问题描述】:

如何根据javascript中的组合获取对象值?

我不知道如何根据提供给函数调用的输入迭代对象并获取对象值。需要一些帮助。

预期的输出应该如下所示。

getValueCreditToBank(obj, "credit", "bank", "SGD");
getValueDebitToBank(obj, "debit", "bank", "THB");

下面的代码取值但要做两个函数,单函数调用有什么方法可以做,

// getValueCreditToBank(obj, "credit", "bank", "SGD");
function getValueCreditToBank(provider, typein, typeout, source){
  return provider.map(item => {
    if (item.country_from[0].paymentIn[0].type == typein 
        && item.country_from[0].currency.includes(source) 
        && item.country_from[0].paymentOut[0].type == typeout) {
      return {
        paymentIn: typein,
        paymentOut: typeout,
        paymentInFee: item.country_from[0].paymentIn[0].fee.number + "%",
        payInSpeed: item.country_from[0].paymentIn[0].speed.number + "days",
        ...item
      }      
    }
   })
  .map(y=>({  
    ...y,
    targetAmountwithPay: y.targetAmount + y.country_from[0].paymentIn[0].fee.number*y.targetAmount/100
  }))
}

// getValueDebitToBank(obj, "debit", "bank", "SGD");
function getValueDebitToBank(provider, typein, typeout, source){
  return provider.map(item => {
    if (item.country_from[0].paymentIn[1].type == typein 
        && item.country_from[0].currency.includes(source) 
        && item.country_from[0].paymentOut[0].type == typeout) {
      return {
        paymentIn: typein,
        paymentOut: typeout,
        paymentInFee: item.country_from[0].paymentIn[1].fee.number + "%",
        payInSpeed: item.country_from[0].paymentIn[1].speed.number + "days",
        ...item
      }      
    }
   })
  .map(y=>({  
    ...y,
    targetAmountwithPay: y.targetAmount + y.country_from[0].paymentIn[0].fee.number*y.targetAmount/100
  }))
}

对象示例:

var obj = [{
    "id": "identity1",
    "fee": '2',
    "rate": '0.5',
    "targetAmount": '1000',
     "country_from": [{
        "currency": [
            "SGD",
            "USD"
        ],
        "paymentIn": [{
            "type": "credit",
            "speed": {
                "unit": "days",
                "number": "1"
            },
            "fee": {
                "type": "%",
                "number": "1.5"
            }
        },{
            "type": "debit",
            "speed": {
                "unit": "days",
                "number": "1"
            },
            "fee": {
                "type": "%",
                "number": "1"
            }
        }],
       "paymentout":[{
          "type":"bank"
       }]
    }]
},
{
    "id": "identity2",
    "fee": '1',
    "rate": '0.5',
    "targetAmount": '1000',
     "country_from": [{
        "currency": [
            "THB",
            "USD"
        ],
        "paymentIn": [{
            "type": "debit",
            "speed": {
                "unit": "days",
                "number": "1"
            },
            "fee": {
                "type": "%",
                "number": "1"
            }
        }
        ],
       "paymentout":[{
          "type":"bank"
       }]
    }]
}]

预期输出:

//getValue(obj, "credit", "bank", "SGD"); should return object as
 {id: "identity1",
 fee: '2',
 rate: '0.5',
 currency: SGD,
 paymentIn: "credit",
 paymentOut: "bank",
 paymentIn Fee: 1.5%,
 targetAmount: 1000,
 targetAmountwithPay: 506.485 //(((targetamount-fee)*rate)+credit fee))}
//getValue(obj, "debit", "bank", "THB"); should return object as
 {id: "identity2",
 fee: '1',
 rate: '0.5',
 currency: THB,
 paymentIn: "debit",
 paymentOut: "bank",
 paymentIn Fee: 1%,
 targetAmount: 1000,
 targetAmountwithPay: 504.49 //(((targetamount-fee)*rate)+credit fee))}

【问题讨论】:

  • 如果country_from数组有多个obj怎么办?
  • @AswinKumar 感谢基于货币(“SGD”)的及时回复,必须对其进行过滤并进行组合,例如对于每个类型输入(信用,借记)和类型输出(银行),应该计算目标金额并返回如图所示的对象
  • @AswinKumar 我已经更新了代码,如果可能请分享 answer.thanks
  • 我们如何在您的输出中提供feerate?查找amount 也是如此。我找不到您必须从原始对象中获取这些信息的位置。为什么数组里面只有一个对象?
  • @iArcadia 道歉,更新了代码 obj

标签: javascript jquery arrays object


【解决方案1】:

我在您的代码中看到的第一个问题是您映射了所有数组,但您只更改了一些元素。

也许您没有注意到这一点,因为您设置的过滤器正在传递所有数组元素,但如果没有,您将在最终数组中看到许多未定义的元素。

所以我建议你更新你的代码引入一个过滤器:

function getValueCreditToBank(provider, typein, typeout, source){
  return provider
    .filter(item => (item.country_from[0].paymentIn[0].type == typein 
        && item.country_from[0].currency.includes(source) 
        && item.country_from[0].paymentOut[0].type == typeout))
    .map(item => ({
        paymentIn: typein,
        paymentOut: typeout,
        paymentInFee: item.country_from[0].paymentIn[0].fee.number + "%",
        payInSpeed: item.country_from[0].paymentIn[0].speed.number + "days",
        ...item
      }))
  .map(y=>({  
    ...y,
    targetAmountwithPay: y.targetAmount + y.country_from[0].paymentIn[0].fee.number*y.targetAmount/100
  }))
}

你在这两个函数中做了几乎相同的任务,并且你没有正确使用参数,所以例如你可以通过typein参数确定paymentIn的索引:

function getValueToBank(provider, typein, typeout, source){
  const paymentInIndex = typein === 'credit' ? 0 : 1;
  return provider
    .filter(item => (item.country_from[0].paymentIn[paymentInIndex].type == typein 
        && item.country_from[0].currency.includes(source) 
        && item.country_from[0].paymentOut[0].type == typeout))
    .map(item => ({
        paymentIn: typein,
        paymentOut: typeout,
        paymentInFee: item.country_from[0].paymentIn[paymentInIndex].fee.number + "%",
        payInSpeed: item.country_from[0].paymentIn[paymentInIndex].speed.number + "days",
        ...item
      }))
}

然后你就可以实现你的功能了:

function getValueCreditToBank(provider, typeout, source){
    return getValueToBank(provider, 'credit', typeout, source)
    .map(y=>({  
        ...y,
        targetAmountwithPay: y.targetAmount + y.country_from[0].paymentIn[0].fee.number*y.targetAmount/100
  }))
}

function getValueDebitToBank(provider, typeout, source){
    return getValueToBank(provider, 'debit', typeout, source)
}

因此,您从原始函数中删除 typein 参数,因为它由函数名称决定。

这只是一个例子,你可以用不同的方式重写,一个更易读的方法是为你传递给过滤和映射数组的箭头函数命名。

【讨论】:

    【解决方案2】:

    这里有三个函数:

    • getValue(obj, pin, pout, currency) 是做aaaall逻辑的那个。
    • getValueCreditToBank(obj, currency)getValue(obj, 'credit', 'bank', currency) 的简写。
    • getValueDeditToBank(obj, currency)getValue(obj, 'debit', 'bank', currency) 的简写。

    该函数目前仅在country_from 数组有一个对象时才有效。

    逻辑很简单:

    • 在对象数组中找到对应的paymentInpaymentOut对象,以及对应的currency
    • 如果找到相应的对象:
      • 计算targetAmountWithPay
      • 返回一个新对象。

    /**
     * Shorthand for getValue() with {pin = "credit"} and {pout = "bank"}.
     * @param {Object[]} obj
     * @param {string} currency
     * @returns {Object}
     */
    function getValueCreditToBank(obj, currency) {
      return getValue(obj, 'credit', 'bank', currency);
    }
    
    /**
     * Shorthand for getValue() with {pin = "debit"} and {pout = "bank"}.
     * @param {Object[]} obj
     * @param {string} currency
     * @returns {Object}
     */
    function getValueDebitToBank(obj, currency) {
      return getValue(obj, 'debit', 'bank', currency);
    }
    
    /**
     * @param {Object[]} obj
     * @param {string} pin
     * @param {string} pout
     * @param {string} currency
     * @returns {Object}
     */
    function getValue(obj, pin, pout, currency) {
      // paymentIn and paymentOut corresponding objects found from function parameters, initialized to undefined.
      let opint, opout;
      
      // The corresponding item found from function parameters.
      const found = obj.find((item) => {
        // Gets paymentIn object from pin parameter.
        opin = item.country_from[0].paymentIn.find((pinItem) => (pinItem.type.indexOf(pin) > -1));
        
        // Gets paymentOut object from pout parameter.
        opout = item.country_from[0].paymentout.find((poutItem) => (poutItem.type.indexOf(pout) > -1));
        
        // If no paymentIn object, or no paymentOut object, or no currency found,
        // we cannot find anything.
        if (item.country_from[0].currency.indexOf(currency) === -1 || !opin || !opout) {
          return false;
        }
        
        return true;
      });
      
      // If a corresponding object is found, creates the returned object.
      if (found) {
        let targetAmountWithPay = (found.targetAmount - found.fee) * found.rate;
        targetAmountWithPay += opin.fee.number * targetAmountWithPay / 100;
      
        return {
          id: found.id,
          fee: parseFloat(found.fee),
          rate: parseFloat(found.rate),
          currency: currency,
          paymentIn: pin,
          paymentOut: pout,
          paymentInFee: `${opin.fee.number}${opin.fee.type}`,
          targetAmount: parseFloat(found.targetAmount),
          targetAmountWithPay: targetAmountWithPay
        };
      }
      
      // If not, returns null.
      return null;
    }
    
    // Tests you gave us.
    console.log(getValueCreditToBank(obj, 'SGD'));
    console.log(getValueDebitToBank(obj, 'THB'));
    
    // Test if nothing is found. Should return null.
    console.log(getValueCreditToBank(obj, 'EUR'));
    console.log(getValueDebitToBank(obj, 'EUR'));
    console.log(getValue(obj, 'credit', 'not-a-bank', 'SGD'));
    console.log(getValue(obj, 'not-a-credit-nor-a-debit', 'bank', 'SGD'));
    <script>
    // I put your object in HTML in order to have two different frames in the snippet.
    const obj = [{
        "id": "identity1",
        "fee": '2',
        "rate": '0.5',
        "targetAmount": '1000',
         "country_from": [{
            "currency": [
                "SGD",
                "USD"
            ],
            "paymentIn": [{
                "type": "credit",
                "speed": {
                    "unit": "days",
                    "number": "1"
                },
                "fee": {
                    "type": "%",
                    "number": "1.5"
                }
            },{
                "type": "debit",
                "speed": {
                    "unit": "days",
                    "number": "1"
                },
                "fee": {
                    "type": "%",
                    "number": "1"
                }
            }],
           "paymentout":[{
              "type":"bank transfer"
           }]
        }]
    },
    {
        "id": "identity2",
        "fee": '1',
        "rate": '0.5',
        "targetAmount": '1000',
         "country_from": [{
            "currency": [
                "THB",
                "USD"
            ],
            "paymentIn": [{
                "type": "debit",
                "speed": {
                    "unit": "days",
                    "number": "1"
                },
                "fee": {
                    "type": "%",
                    "number": "1"
                }
            }
            ],
           "paymentout":[{
              "type":"bank transfer"
           }]
        }]
    }];
    </script>

    如果您想获得有关您尝试自己执行的功能的更新的答案,请查看@Mario Santini's answer

    【讨论】:

      猜你喜欢
      • 2019-02-14
      • 2016-03-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-09-12
      • 2021-10-02
      • 1970-01-01
      • 2020-07-16
      相关资源
      最近更新 更多