#javascript #arrays #validation #javascript-objects
#javascript #массивы #проверка #javascript-объекты
Вопрос:
В настоящее время я работаю над инструментом проверки javascript, который принимает входное значение адреса и сравнивает его со встроенным массивом объектов. У меня частично работает инструмент, и он отображает true, если все значения в поле ввода соответствуют первому объекту в массиве, но если это не удается, я хочу, чтобы он перебирал следующий объект в массиве, пока не найдет совпадение и не покажет true или не соответствует ни одному из объектов и может отображать true.ложь. Я попытался использовать для этого цикл for, но не смог заставить его работать. Я приложил код в качестве доказательства того, о чем я говорю, вплоть до того момента, когда я добавил цикл for, потому что он работает, пока я этого не сделаю. Заранее извините, я все еще новичок в Java script и, возможно, не знаю лучших практик, но любая помощь принимается!
function myFunction() {
var str = document.getElementById('address').value;
var res = str.split(" ");
var streetNumber = res[0];
var x = streetNumber;
var y = phaseOne[0].streetNumberLow;
var z = phaseOne[0].streetNumberHigh;
if(x >= y amp;amp; x <= z) {
if (res[1] == phaseOne[0].streetName){
if(res[2] == phaseOne[0].streetCode){
if(res[3] == phaseOne[0].city){
if(res[4] == phaseOne[0].state){
if(res[5] == phaseOne[0].zipCode) {
var w = "true";
} else {
var w = "false";
}
} else {
var w = "false";
}
} else {
var w = "false";
}
} else {
var w = "false";
}
} else {
var w = "false";
}
} else {
var w = "false";
}
document.getElementById('demo').innerHTML = w;
};
var phaseOne = [
{
"streetNumberLow": "1",
"streetNumberHigh": "436",
"streetName": "barnhart",
"streetCode": "rd",
"city": "waynesburo",
"state": "va",
"zipCode": "22980"
},
{
"streetNumberLow": "437",
"streetNumberHigh": " 1338",
"streetName": "barnhart",
"streetCode": "rd",
"city": "fort defiance",
"state": "va",
"zipCode": "24437"
},
{
"streetNumberLow": "1339",
"streetNumberHigh": "1372",
"streetName": "barnhart",
"streetCode": "rd",
"city": "crimora",
"state": "va",
"zipCode": "24431"
}
];
@import url('https://fonts.googleapis.com/css2?family=Bebas Neueamp;family=Poppins:wght@400;700amp;display=swap');
/* Global */
* {
margin: 0;
padding: 0;
font-family: 'Bebas Neue', cursive;
/* box-sizing: border-box; */
/* overflow: hidden; */
}
#address-checker {
height:20vh;
width: 60%;
margin: auto;
margin-top: -3vh;
padding: 3vw;
background-color: #fff;
position: relative;
z-index: 1;
box-shadow: 0 .5rem 1rem rgba(0, 0, 0, 0.5);
}
.checker-container {
height: 20vh;
}
.address-header {
margin: 1vh;
text-align: center;
color: #2277AE;
letter-spacing: 1px;
font-size: clamp( 1.2rem, 2.75vw, 3.5rem);
}
.address-checker-input {
padding: 3vh 0;
}
.address-box {
margin: 3vh 0 0 10vw ;
width: 60%;
padding: .75rem 0 .75rem .5rem;
border-radius: 10px;
border: #2277AE 2px solid;
color: #2277AE;
}
.address-box:hover {
border-color: #FEA00B;
transition: .2s;
}
.go-btn {
background-color: #2277AE;
padding: .75rem;
border-radius: 10px;
border: #2277AE 2px solid;
color: #fff;
}
.go-btn:hover {
border-color: #FEA00B;
transition: .2s;
}
<section id="address-checker">
<div class="checker-container">
<h1 class="address-header">
Is Fiber to the Home available for you?
</h1>
<div class="address-checker-input">
<input
id="address"
type="text"
name="searchaddress"
placeholder="Street Address, City, State, Zip Code"
class="address-box"
/>
<button class="go-btn" onclick="myFunction()">Go</button>
</div>
<p id="demo"></p>
</div>
</section>
Комментарии:
1. if (res[1] == PhaseOne[0].Название улицы){ if(res[2] == PhaseOne[0].Уличный код){… вы слышали о логическом И операторе?
2. да, но просто хотел собрать это вместе, потому что мой последний вопрос был закрыт, потому что в нем было недостаточно информации, и я просто хотел показать свою линию мышления. Я просто хотел рабочую модель для тестирования, а затем вернуться и очистить ее.
3. вы правы
4. но все же о вопросе.. есть какие-нибудь мысли, кроме того, что я убиваю его повторяющимся кодом?
5. В вашем коде нет циклов. Покажите нам код, который не работает.
Ответ №1:
Когда вы теряетесь в своем собственном коде, попробуйте создать небольшие функции, которые делают что-то одно. Это упростит отладку, и вы сразу узнаете, где искать.
Например, вы можете создать функцию, которая принимает адрес в виде строки и возвращает объект со всеми его свойствами, поэтому вам не придется беспокоиться об этой части где-либо еще в вашем коде, и если вам нужно ее настроить, она будет здесь:
function parseAddressString(str) {
// Check out how this Regex works here: https://regex101.com/r/1UYeEM/2
var matches = str.match(/(?<streetNumber>d )s (?<streetName>[ws-] )s (?<streetCode>w ),?s (?<city>[ws-] ),?s (?<state>w ),?s (?<zipCode>d )/);
if (matches) { return matches.groups; }
return false; // The address did not match the Regex
}
console.log(parseAddressString('33 Barnhart rd, Waynesburo, VA, 22980'));
console.log(parseAddressString('555 North Dakota st, New-York, NY, 77777'));
.as-console-wrapper { max-height: 100% !important; }
Получив это, вы можете создать функцию, которая принимает один объект adress, один объект «phase» и возвращает, совпадают ли они:
function doesStringMatch(a, b) {
return a.toLowerCase().includes(b.toLowerCase());
} function parseAddressString(str) { var matches = str.match(/(?<streetNumber>d )s (?<streetName>[ws-] )s (?<streetCode>w ),?s (?<city>[ws-] ),?s (?<state>w ),?s (?<zipCode>d )/); if (matches) { return matches.groups; } return false; }
function doesAddressMatchPhase(address, phase) {
return address amp;amp;
address.streetNumber >= phase.streetNumberLow amp;amp;
address.streetNumber <= phase.streetNumberHigh amp;amp;
doesStringMatch(address.streetName, phase.streetName) amp;amp;
doesStringMatch(address.streetCode, phase.streetCode) amp;amp;
doesStringMatch(address.city, phase.city) amp;amp;
doesStringMatch(address.state, phase.state) amp;amp;
doesStringMatch(address.zipCode, phase.zipCode);
}
var phase = {"streetNumberLow": "1", "streetNumberHigh": "436", "streetName": "barnhart", "streetCode": "rd", "city": "waynesburo", "state": "va", "zipCode": "22980"};
var address1 = parseAddressString('33 Barnhart rd, Waynesburo, VA, 22980');
console.log( doesAddressMatchPhase(address1, phase) ); // true
var address2 = parseAddressString('555 North Dakota st, New-York, NY, 77777');
console.log( doesAddressMatchPhase(address2, phase) ); // false
И после этого создайте функцию, которая проверяет, соответствует ли одна из фаз:
function isEligible(str) {
var address = parseAddressString(str);
return phaseOne.some(function(phase) {
return doesAddressMatchPhase(address, phase);
});
}
Полная демонстрация
/* Unchanged */ var phaseOne = [{"streetNumberLow": "1", "streetNumberHigh": "436", "streetName": "barnhart", "streetCode": "rd", "city": "waynesburo", "state": "va", "zipCode": "22980"},{"streetNumberLow": "437", "streetNumberHigh": " 1338", "streetName": "barnhart", "streetCode": "rd", "city": "fort defiance", "state": "va", "zipCode": "24437"},{"streetNumberLow": "1339", "streetNumberHigh": "1372", "streetName": "barnhart", "streetCode": "rd", "city": "crimora", "state": "va", "zipCode": "24431"}];
function parseAddressString(str) {
var matches = str.match(/(?<streetNumber>d )s (?<streetName>[ws-] )s (?<streetCode>w ),?s (?<city>[ws-] ),?s (?<state>w ),?s (?<zipCode>d )/);
if (matches) { return matches.groups; }
return false;
}
function doesStringMatch(a, b) {
return a.toLowerCase().includes(b.toLowerCase());
}
function doesAddressMatchPhase(address, phase) {
return address amp;amp;
address.streetNumber >= phase.streetNumberLow amp;amp;
address.streetNumber <= phase.streetNumberHigh amp;amp;
doesStringMatch(address.streetName, phase.streetName) amp;amp;
doesStringMatch(address.streetCode, phase.streetCode) amp;amp;
doesStringMatch(address.city, phase.city) amp;amp;
doesStringMatch(address.state, phase.state) amp;amp;
doesStringMatch(address.zipCode, phase.zipCode);
}
function isEligible(str) {
var address = parseAddressString(str);
return phaseOne.some(function(phase) {
return doesAddressMatchPhase(address, phase);
});
}
function myFunction() {
var str = document.getElementById('address').value, eligible = isEligible(str);
document.getElementById('demo').innerHTML = eligible ? "true" : "false";
}
<!-- Unchanged HTML amp; CSS --> <section id="address-checker"> <div class="checker-container"> <h1 class="address-header"> Is Fiber to the Home available for you? </h1> <div class="address-checker-input"> <input id="address" type="text" name="searchaddress" placeholder="Street Address, City, State, Zip Code" class="address-box"/> <button class="go-btn" onclick="myFunction()">Go</button> </div><p id="demo"></p></div></section><style>@import url('https://fonts.googleapis.com/css2?family=Bebas Neueamp;family=Poppins:wght@400;700amp;display=swap');/* Global */*{margin: 0; padding: 0; font-family: 'Bebas Neue', cursive;/* box-sizing: border-box; */ /* overflow: hidden; */}#address-checker{height:20vh; width: 60%; margin: auto; margin-top: -3vh; padding: 3vw; background-color: #fff; position: relative; z-index: 1; box-shadow: 0 .5rem 1rem rgba(0, 0, 0, 0.5);}.checker-container{height: 20vh;}.address-header{margin: 1vh; text-align: center; color: #2277AE; letter-spacing: 1px; font-size: clamp( 1.2rem, 2.75vw, 3.5rem);}.address-checker-input{padding: 3vh 0;}.address-box{margin: 3vh 0 0 10vw ; width: 60%; padding: .75rem 0 .75rem .5rem; border-radius: 10px; border: #2277AE 2px solid; color: #2277AE;}.address-box:hover{border-color: #FEA00B; transition: .2s;}.go-btn{background-color: #2277AE; padding: .75rem; border-radius: 10px; border: #2277AE 2px solid; color: #fff;}.go-btn:hover{border-color: #FEA00B; transition: .2s;}</style>
Комментарии:
1. Большое тебе спасибо, чувак! вы действительно потратили время, чтобы объяснить все подробно, и это наверняка поможет мне двигаться вперед! спасибо, что нашли время помочь!
2. У меня есть вопрос о допустимой функции. метод .some() является логическим и предоставляет значение, которое вставляется в DOM Я понимаю это, но я не совсем понимаю, как это выбирает, с каким объектом в PhaseOne сопоставлять. План заключается в том, чтобы функция matchPhase обрабатывалась для следующего объекта, если первый сбой. Я создам функцию для циклического перебора объектов в массиве PhaseOne и попытаюсь заставить ее работать, но если бы вы могли объяснить последние 2 строки функции isEligible, это действительно помогло бы. Спасибо!
3. неважно.. понял это.. без запятых во входных данных он вернет false, даже если входные данные верны, потому что он распознает неправильный пробел, но я могу это исправить. еще раз спасибо.
4. Точно,
.some
перебирает массив PhaseOne и возвращает true, как только один из них совпадает. Дайте мне знать, если вам нужна помощь с пробелами, но да, возможноparseAddressString
, требуется небольшая настройка. Не стесняйтесь использовать ссылку Regex101, указанную в первом фрагменте, введите кучу допустимых и недопустимых входных данных и настройте регулярное выражение, наблюдая, что соответствует или нет5. Именно то, что я делал, спасибо за помощь!