ฉันจะปรับปรุงและย่อรหัสบล็อกนี้ให้สั้นลงได้อย่างไร [ปิด]


9

ฟังก์ชันนี้ใช้สตริงของ DNA เช่น 'GTCA' และส่งกลับอาร์เรย์ที่มีคู่ DNA ที่จับคู่อย่างถูกต้อง

function pairDNA(dna) {

  const pairs = []

  for (let i = 0; i < dna.length; i ++) {

    if (dna[i] === "C" | dna[i] === "c") {
      pairs.push("CG");
    } else if (dna[i] === "G"| dna[i] === "g") {
      pairs.push("GC");
    } else if (dna[i] === "T"| dna[i] === "t") {
    pairs.push("TA");
    } else if (dna[i] === "A"| dna[i] === "a") {
      pairs.push("AT");
    }
  }

return pairs;
}

สิ่งนี้ถูกต้อง อย่างไรก็ตามฉันพยายามค้นหาวิธีที่สั้นกว่าง่ายกว่าในการเขียน ใครสามารถช่วยฉันด้วยสิ่งที่ฉันควรจะใช้?


1
ใช้วิธีนี้ได้อย่างง่ายดาย dna [i] .toLowerCase ()
Thaier Alkhateeb

9
หากรหัสของคุณใช้งานได้และคุณต้องการการปรับปรุงลองcodereview.stackexchange.com
Peter Collingridge

ฉันไม่คิดว่ารหัสนี้ทำงานได้ตามที่ต้องการ| อย่าทำตรรกะหรือใน Javascript เช่น||
ROOT

2
@mounounothman - จริง แต่ทั้งคู่จะทำงานในรหัสนั้น ( ||จะดีกว่า)
TJ Crowder

คำตอบ:


14

คุณสามารถปรับปรุงโค้ดของคุณในขั้นตอนต่อไปนี้:

  • เมื่อมีหลายคำสั่งถ้าและทั้งหมดมีโครงสร้างเดียวกันคุณอาจต้องใช้วัตถุ
  • คุณต้องตรวจสอบทั้งตัวพิมพ์ใหญ่และตัวพิมพ์เล็ก เพียงใช้toLowerCase()กับอินพุต
  • คุณสามารถsplitสตริงและmap()มันแทนที่จะสร้างpush()ค่าอาร์เรย์ลงในมัน

function pairDNA(dna) {
  const obj = {
    c: 'CG',
    g: 'GC',
    t: 'TA',
    a: "AT"
  }
  return dna.split('').map(x => obj[x.toLowerCase()])

}

ถ้าสตริงอาจมีสิ่งอื่นที่ตัวอักษรที่เฉพาะเจาะจงแล้วคุณจะต้องค่าหลังจากที่filter()undefinedmap

return dna.split('').map(x => obj[x.toLowerCase()]).filter(x => x !== undefined)

อีกอย่างที่ดีกว่าถูกกล่าวถึงโดย @RobG ในความคิดเห็นที่เราสามารถลบตัวอักษรที่ไม่ต้องการออกจากสตริงก่อนที่จะวนลูปผ่าน

return dna
        .toLowerCase()
        .replace(/[^cgta]/g,'')
        .split('')
        .map(x => obj[x])

1
หากดีเอ็นเอมีอักขระที่ไม่อยู่ในรายการคุณจะมีundefinedค่าในอาร์เรย์สุดท้ายของคุณ
เกรกอรี่ NEUT

1
@ GrégoryNEUTเพิ่มการแก้ไขสำหรับกรณีนั้นในคำตอบของฉัน
Maheer Ali

หรือคุณสามารถดำเนินการกับสตริงdna.toLowerCase().replace(/[^cgta]/g,'')...ได้ล่วงหน้า ;-)
RobG

@RobG ชอบมันมาก ฉันเพิ่มมันเข้าไปแล้วคำตอบของฉัน
Maheer Ali

1
ฉันพลาดไปว่ามันเป็นสตริง :-) FWIW เป็นวิธีที่มากขึ้น Unicode [...dna]ง่ายของสตริงแยกออกเป็นอาร์เรย์ในขณะนี้คือ มันไม่ทำลายคู่ของตัวแทน (หรือArray.fromซึ่งจะเป็นประโยชน์โดยเฉพาะอย่างยิ่งถ้าคุณกำลังจะ map: Array.from(dna, mappingFunction).) (ไม่ทุกคนที่เกี่ยวข้องที่นี่ผมถือว่าdnaมีเพียงc, g, tและa.)
TJ เด

3

ฉันอาจจะ:

  1. ใช้การfor-ofวนซ้ำ (หรือการจับคู่กับการกรองที่เป็นไปได้)

  2. ใช้วัตถุค้นหาหรือแผนที่

  3. ทำสตริงตัวพิมพ์เล็กหรือตัวพิมพ์ใหญ่เมื่อสลับ / ค้นหา (แต่รายการที่ซ้ำกันในสวิตช์ / ค้นหาทำงานด้วย):

หากคุณรู้ว่าdnaจะมีเพียงc/ C, g/ G, t/ T/ หรือa/ A(ซึ่งตามที่ฉันเข้าใจเป็นจริงของ DNA ;-)) จากนั้นคุณสามารถใช้Array.fromกับคุณสมบัติการทำแผนที่ด้วยวัตถุค้นหา / แผนที่:

const table = {
    c: "CG",
    g: "GC",
    t: "TA",
    a: "AT"
};

function pairDNA(dna) {
  return Array.from(dna, entry => table[entry.toLowerCase()]);
}                                                                                                                           

ฉันใช้Array.fromเพราะมันจะแบ่งสตริงในจุดรหัสไม่ใช่แค่หน่วยรหัส (ไม่แยกคู่ตัวแทน) และมีคุณสมบัติการทำแผนที่หากคุณมีฟังก์ชั่นการทำแผนที่ (โดยทั่วไปArray.from(str, mappingFunction)จะเป็น[...str].map(mappingFunction)แต่ไม่มีอาเรย์กลาง) อาจไม่ใช่ทุกสิ่งที่เกี่ยวข้องในที่นี้เนื่องจากเนื้อหาของสตริงของคุณ แต่อาจมีความสำคัญหากสตริงของคุณอาจมีคู่ตัวแทน

หรือด้วยMap:

const table = new Map([
  [c, "CG"],
  [g, "GC"],
  [t, "TA"],
  [a, "AT"]
]);

function pairDNA(dna) {
  return Array.from(dna, entry => table.get(entry.toLowerCase()));
}                                                                                                                           

หากคุณไม่สามารถทำการสันนิษฐานได้ให้เพิ่ม.filterเพื่อกรองสิ่งที่ไม่มีการแข่งขัน:

function pairDNA(dna) {
  return Array.from(dna, entry => table.get(entry.toLowerCase())).filter(Boolean);
  // or if using an object: return dna.map(entry => table[entry.toLowerCase()]).filter(Boolean);
}

หรือถ้าคุณต้องการหลีกเลี่ยงการสร้างอาร์เรย์พิเศษที่filterจะสร้างติดกับfor-of(หรือของคุณfor):

const table = {
    c: "CG",
    g: "GC",
    t: "TA",
    a: "AT"
};

function pairDNA(dna) {
  const pairs = [];

  for (const entry of dna) {
    const value = table[entry.toLowerCase()];
    if (value) {
      pairs.push(value);
    }
  }
  return pairs;
}

2

คุณสามารถใช้การจับคู่การค้นหาเพื่อทำให้การวนซ้ำง่ายขึ้น:

function pairDNA(dna) {

  const pairs = [], key = { G: "GC", C: "CG", A: "AT", T: "TA" };

  for (let i = 0; i < dna.length; i ++)
    pairs.push(key[dna[i].toUpperCase()]);
  return pairs;
}

นั่นเป็นเรื่องที่น่าสนใจฉันไม่คิดว่าจะทำแบบนี้ขอบคุณ!
CocoFlade

2

อาจไม่สั้นลง แต่สามารถบำรุงรักษาได้มากกว่า

function pairDNA(dna) {
  const map = {
    C: 'CG',
    c: 'CG',
    G: 'GC',
    g: 'GC',
    T: 'TA',
    t: 'TA',
    A: 'AT',
    a: 'AT',
  };

  return dna.split('').reduce((tmp, x) => {
    if (map[x]) {
      tmp.push(map[x]);
    }

    return tmp;
  }, []);
}

คุณสามารถทำได้:

function pairDNA(dna) {
  const map = {
    c: 'CG',
    g: 'GC',
    t: 'TA',
    a: 'AT',
  };

  return dna.split('').reduce((tmp, x) => {
    if (map[x].toLowerCase()) {
      tmp.push(map[x]);
    }

    return tmp;
  }, []);
}

2

คุณสามารถลองใช้switch caseและ a forEachfuncion เช่นนี้:

function pairDNA(dna) {
  let pairs = [];

  dna.forEach( dnaValue => {
    switch (dnaValue.toLowerCase()) {
      case "c":
        pairs.push("CG");
        break;
      case "g":
        pairs.push("GC");
        break;
      case "t":
        pairs.push("TA");
        break;
      case "a":
        pairs.push("AT");
        break;
    }
  })

  return pairs;
}

1

คุณสามารถพิมพ์เล็กสตริงที่จะช่วยให้คุณลบการตรวจสอบของตัวพิมพ์ใหญ่:

function pairDNA(dna) {
  dna = dna.toLowerCase();
  const pairs = []
  for (let i = 0; i < dna.length; i ++) {
   if (dna[i]=== "c") {
     pairs.push("CG");
   } else if (dna[i]dna[i] === "g") {
     pairs.push("GC");
   } else if (dna[i] === "t") {
     pairs.push("TA");
   } else if (dna[i] === "a") {
     pairs.push("AT");
   }
 }

 return p;
}

1
const lookup = {
    c: "CG", 
    g: "GC", 
    t: "TA", 
    a: "AT"
};

function pairDNA(dna) {  

  const pairs = [];

  for (let i = 0; i < dna.length; i ++) {
     pairs.push( lookup[dna[i].toLowerCase()] );
  }

  return pairs;

}
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.