Jump to content
Jeovane Carvalho

Pegar variáveis de um array e enviar dentro do bind_param no sql select usando a cláusula IN (?)

Recommended Posts

Salve pessoal  tudo bem !

Depois de muito tempo venho aqui pedir uma ajuda , bem vamos lá...

Eu tenho uma classe POO e nela pego algumas variáveis que vem como array e uso o implode para enviar através do load do javascript.

Até aí tranquilo, eu resgato com $_GET  usando o explode, e depois uso implode para separar elas novamente.

Montei essa rotina toda por se tratar de uma o paginação se reload , bem dinâmica , só que ao passar os parâmetros e as variáveis no bind_param da erro de parâmetros, dizendo que :

 

Warning: mysqli_stmt::bind_param(): Number of variables doesn't match number of parameters in prepared statement

E entendi que o erro diz que o número de parametros não condiz com o número de variáveis, E AI QUE ENTRA A MINHA DOR DE CABEÇA...

Mesmo eu usando implode eu consigo separar as variáveis mas dando um var_dump elas  ficam juntas  e a execução do prepare lê como uma única variável.

Segue o código abaixo:

 

  <?php

  class  DadosFiltroBusca  {
    private $conecta_banco;

    public function __construct(){
      $this->conecta_banco= new Conexao();
      $this->conecta_banco->Conectar();
    }	
    public $ativo;
    public $negocio ;
    public $tipo;
    public $cidade;
    public $bairro;
    public $id_negocio;
    public $id_tipo;
    public $id_cidade;
    public $id_bairro;
    public $foto;
    public $where;
    public $sqlT_1;
    public $sqlT_2;
    public $total;
    public $current_page;
    public $get_total_rows;
    public $item_per_page;
    public $total_pages;
    public $total_records;
    public $pgst;
    public $page_number;
    public $page_position ;
    public $filtro_dados;
    public $site;

    public function BuscarFiltroBusca(){
      $result=$this->conecta_banco->banco; 

      $this->item_per_page = 4;
      if(isset($_POST["page"])){
        $this->page_number =(isset($_POST['page'])) ? (int)$_POST['page'] : 1;
        if(!is_numeric($this->page_number)){die('Página inválida!');} //incase of invalid page number
      }else{
        $this->page_number = 1;
        //if there's no page number, set it to 1
      }  

      $negocio   = $_GET['negocio'];

      $this->id_tipo= explode(",",$_GET['tipo']);		
      $this->id_cidade=explode(",",$_GET['cidade']);
      $this->id_bairro=explode(",",$_GET['bairro']);





      




      $idi=implode('', $this->id_tipo);





      echo "<br /><br />";

      $in=(is_array($this->id_tipo) ? count($this->id_tipo):0);

      $id_tipo = implode(',', array_fill(0, $in, '?'));
      
      echo " :: " . $id_tipo_2 =join('', array_fill(0, 1, $idi));
      
      echo " :: ".$types =str_repeat('s',$in);

      echo "<br /> VAR:: ".$tipo =str_repeat(''.$id_tipo_2.'',1);  
      
      var_dump ($tipo );

      $idi1='5';
      $idi2='11';

      foreach ($this->id_cidade as $key=> $id_cidade):
      foreach ($this->id_bairro as $key=> $id_bairro):


      $ativo='1';
      "%".$negocio."%";
      $id_tipo;  
      $id_cidade;
      $id_bairro;

      echo "<br /><br />RESULTADO :: ". $t='ss'.$types.'ss',$ativo,$negocio,$tipo ,$id_cidade,$id_bairro."<br /><br />";

      $where = " i.ativo =? ";
      if( $negocio)  {
        $where .="AND i.id_negocio_tipo LIKE ?";
      }if( $id_tipo )  {
        $where .=" AND i.id_tipo_imovel IN ($id_tipo)";
      }
      if( $id_cidade ) {
        $where .=" AND i.id_cidade=?";
      }
      if($id_bairro) {
        $where .=" AND i.bairro=?";
      }

      $sqlT_1 =$result->prepare("SELECT i.*, t.tipo_nome, b.bairro, n.tipo, c.cidade FROM imoveis
      i LEFT JOIN negocio_tipo n ON (n.id = i.id_negocio_tipo)
      LEFT JOIN imoveis_tipo t ON (t.id = i.id_tipo_imovel)
      LEFT JOIN cidades c ON (c.id = i.id_cidade)
      LEFT JOIN bairros b ON (b.id = i.bairro)
      WHERE ".$where."");

      $sqlT_1->bind_param('ss'.$types.'ss',$ativo,$negocio,$tipo ,$id_cidade,$id_bairro);
      $sqlT_1->execute();
      $this->sqlT_1 = $sqlT_1->get_result();

      $this->get_total_rows+=$this->sqlT_1->num_rows;
      if($this->get_total_rows >0 ){
        $this->total_pages = ceil($this->get_total_rows / $this->item_per_page);
      }
      $this->sqlT_1->num_rows;
      //break records into pages

      //get starting position to fetch the records
      if($this->get_total_rows > 0 ){
        $this->page_position = (($this->page_number * $this->item_per_page) -$this->item_per_page);
        $this->pgst = ceil($this->get_total_rows  / $this->item_per_page);
      }
      $sqlT_1->close();

      endforeach;
      endforeach;




      $sqlT_2 =$result->prepare("SELECT i.id, i.valor,i.locacao, i.foto_exibicao,i.latitude,i.longitude, i.quartos, i.garagem,i.mapa, i.codigo, t.tipo_nome, n.tipo AS    negocio, c.cidade, c.uf, b.bairro FROM imoveis i
      LEFT JOIN negocio_tipo n ON (n.id = i.id_negocio_tipo)
      LEFT JOIN imoveis_tipo t ON (t.id = i.id_tipo_imovel)
      LEFT JOIN cidades c ON (c.id = i.id_cidade)
      LEFT JOIN bairros b ON (b.id = i.bairro)
      WHERE ".$where." ORDER BY i.id DESC LIMIT ?,?");
      $sqlT_2->bind_param('sssssss',$ativo,$negocio,$idi,$id_cidade,$id_bairro,$this->page_position,$this->item_per_page);
      $sqlT_2->execute();
      $this->sqlT_2=$sqlT_2->get_result();




    }
  }

  ?>

Vejam no código que existem 2 consultas, um select é para montar a páginação sem reflesh e a outra é para buscar os dados do filtro de busca , e para deixar mais claro, se eu colocar no lugar cláusula IN em vez de IN (?) colocar IN ($variavel ) que já foi separada com o implode ela busca perfeitamente as informações , exemplo abaixo:

 

$where = " i.ativo =? ";
    if( $negocio)  {
    $where .="AND i.id_negocio_tipo LIKE ?";
    }if( $id_tipo )  {
    $where .=" AND i.id_tipo_imovel IN (?)"; AQUI É AONDE TEM O ARRAY, E AS OUTRAS ESTÃO SEM ARRAYS PARA TESTAR APENAS ESSA VARIÁVEL
    }
    if( $id_cidade ) {
    $where .=" AND i.id_cidade=?";
    }
    if($id_bairro) {
    $where .=" AND i.bairro=?";
    }

Acima da aquele erro de; Warning: mysqli_stmt::bind_param(): Number of variables doesn't match number of parameters in prepared statement

Mas agora logo abaixo vai de boa e forma a paginação e trás os valores:

 

$where = " i.ativo =? ";
    if( $negocio)  {
    $where .="AND i.id_negocio_tipo LIKE ?";
    }if( $id_tipo )  {
    $where .=" AND i.id_tipo_imovel IN ($id_tipo)";
    }
    if( $id_cidade ) {
    $where .=" AND i.id_cidade=$id_cidade";
    }
    if($id_bairro) {
    $where .=" AND i.bairro=$id_bairro";
    }

 

E vi que o problema esta aqui abaixo:

$sqlT_1->bind_param('ss'.$types.'ss',$ativo,$negocio,AQUI É A VARIÁVEL COM ARRAY -> $tipo ,$id_cidade,$id_bairro);

Notem que esta variável dentro dos parâmetros ($types) ela trás o número de parâmetros conforme o critério de busca do filtro de busca, E este parametro como variável eu pego com o str_repeat

E  se eu montar as variáveis manualmente tipo > $tipo1=15'; e $tipo2='11'; e jogar lá no bind param ela chama de boa tipo assim :

 

$tipo1='15'; 
$tipo2='11'

 $sqlT_1->bind_param('ss'.$types.'ss',$ativo,$negocio,$tipo1,$tipo2 ,$id_cidade,$id_bairro);

se eu fizer desta forma chama perfeitamente, e vi que o problema é na hora de separar as variáveis do array.

Já usei serialize, join, json_decode e nada .

Se alguém souber de como contornar agradeço. E desculpe pela imensa explicação , mas é para entederem melhor :)

Obrigado !

 

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

  • Similar Content

    • By granderodeo
      Estou tentando pegar dados de duas tabelas logo no inicio da sessão quando o usuário realiza o login, quando utilizo o 
      SELECT * FROM usuarios, orders WHERE email = '$login' and senha= '$senha' Consigo realizar o login tranquilamente, até ai de boa, mais quando modifico o código para
       
      $comando="SELECT * FROM usuarios INNER JOIN orders ON usuarios.id_usuario = orders.id_usuario WHERE email.usuarios='$login' and senha.usuarios='$senha'"; Ele só me deixa fazer login se o usuário já tiver algum orders (pedido). O que estou tentando fazer é assim que o usuário loga, mostre também os pedidos que ele já fez etc, que são dados que estão em outra tabela. Alguém consegue ver meu erro?
    • By cleomarjose
      Boa noite
      preciso de uma ajuda de vocês, montando um raspador de site e quero que as informaçções fiquem organizadas, não consigo descobrir como coloco as id valorCep e valorComplCep na mesma linha, obrigado pela ajuda
       
                 <h1> <p id="valorCep">                 </p>    </h1>
                 <h1> <p id="valorComplCep">            </p>    </h1>
                 
      <input type="text" id="cependseg__numero" name="cependseg__numero" autocomplete="off" class="input-cep" maxlength="5" onkeyup="autoTabSelection( get(&#39;cependseg__numero&#39;) , get(&#39;cependseg__complemento&#39;), event);" value="29092" onchange="javascript:atualizarHiddenCep(&#39;cependseg&#39;);javascript:limparCampos([&#39;estabelecimento&#39;,&#39;codigoLocalDesconto&#39;,&#39;codigoTipoLocalDesconto&#39;,&#39;clausulaServico&#39;,&#39;codigoClausulaServico&#39;]);javascript:acionarBuscaDiretaPorCep_cependseg(this);" onblur="javascript:setValorFromId(&#39;cependseg&#39;,preencherAEsquerda(getValorFromId(&#39;cependseg&#39;),3,&#39;0&#39;));javascript:atualizarHiddenCep(&#39;cependseg&#39;);" onkeypress="return isNumber(event);"> - <input type="text" id="cependseg__complemento" name="cependseg__complemento" autocomplete="off" class="input-complemento_cep" maxlength="3" value="065" onchange="javascript:atualizarHiddenCep(&#39;cependseg&#39;);javascript:limparCampos([&#39;estabelecimento&#39;,&#39;codigoLocalDesconto&#39;,&#39;codigoTipoLocalDesconto&#39;,&#39;clausulaServico&#39;,&#39;codigoClausulaServico&#39;]);" onblur="javascript:setValorFromId(&#39;cependseg&#39;,preencherAEsquerda(getValorFromId(&#39;cependseg&#39;),5,&#39;0&#39;));javascript:atualizarHiddenCep(&#39;cependseg&#39;); javascript:acionarBuscaDiretaPorCep_cependseg(this);" onkeypress="return isNumber(event);"><div class="div-botoes-atributo div-botao-encontrarcep"><div class="btCor3"></div>
      <script>
               capturando = document.getElementById('cependseg__numero').value;
          document.getElementById('valorCep').innerHTML = capturando;
               capturando = document.getElementById('cependseg__complemento').value;
          document.getElementById('valorComplCep').innerHTML = capturando;
          </script>
    • By srawolf
      Eu tenho uma tabela, essa tabela vem com o campo nome e matricula do banco de dados (fiz em mongodb), eu ia colocar uns inputs para notas e ser enviado no text do email, mas ele repete a primeira linha da tabela
      Estou usando, node.js, nodemailer, mongodb
      o email não aparece na tela, so no banco de dados e eu puxo ele quando vou enviar o email, como eu posso identificar esses inputs para que cada email receba sua respectiva nota?
    • By Fernando Rafael
      Estou tendo problemas com a leitura de porta serial com PHP, consigo facilmente escrever na mesma, mas sempre que no comando de abertura da porta eu coloco que haverá permissão de leitura o PHP trava e fica carregando infinitamente, e a porta fica bloqueada e só libera quando reiniciado o computador.
       
      Segue o cod:
      exec('MODE COM1:9600,n,8,1'); //seta configuração na porta COM $fp=fopen("COM1","r+b"); if(!$fp) {     echo("Erro ao abrir a porta com1");     exit; } else {         echo("COM1 aberta <br>"); } fwrite($fp,Chr(5));  //escrevendo valor na porta sleep(1); //pausa para retorno dos dados echo (fgets($fp)); fclose($fp); já tentei  colocar:
      fopen("COM1", "r+b");
      fopen("COM1", "r+t");
      fopen("COM1", "r");
      fopen("COM1", "w+");
      fopen("COM1", "r+");
       
      para escrever consigo normal, com o fopen("COM1", "w");.  mas já para ler.....
       
      Notei que na internet tem muito sobre esse problema, inclusive falaram em permissões de usuário, sendo que nos casos em que conseguiram, estavam usando o Linux.
      Eu estou usando o W7 e W10 com PHP 5.2, se for o caso de permissões, como resolvo isso? preciso configurar mais alguma coisa no php.ini?
       
      Também já tentei usar uma classe: phpSerial
       
      Mas retorna o seguinte erro:
      Warning: Reading serial port is not implemented for Windows in C:\Program Files (x86)\Apache Software Foundation\Apache2.2\htdocs\balanca\php_serial.class.php on line 503
       
       
    • By rogerblower
      Pessoal tenho a seguinte tabela
      id | id_etapa | id_evento | posicao | nome | pontos
      1  |  1             |        2         |   1           | joao      |  10
      2  |  1             |        2         |   2           | pedro    |  9
      3  |  1             |        2         |   3           | maria    |  8
      4  |  1             |       2          |   4           | jose       |  7
      5  |  2             |      2          |   3           | joao       |  8
      6  |  2             |  2              |   1           | pedro    | 10
      7  |  2             |   2             |  2            | maria    |  9
      8  |  2             |  2              |   4          | jose        |  7
       
      O resultado da consulta pretendido é este
      Pos  |  nome |   pontos
      1      |  pedro   | 19
      2      |   joao   | 18
      3      |  maria  |  17
      4      |  jose  |  14
       
      Com esta consulta não ordenando a coluna posicao como esperado, ela repete a posicao e não faz a soma, ex:
       1     joao     10
       1     pedro     10
      $pontuacaoa = $pdo->prepare("SELECT * FROM contador WHERE id_evento = '$id_evento' GROUP BY nome, posicao ORDER BY pontos DESC posicao ASC"); Com esta outra consulta a soma esta correta o agrupamento nome esta correto, não se repetem, mas a coluna posicao fica fora de ordem;
       
      $pontuacaoa = $pdo->prepare("SELECT * FROM contador WHERE id_evento = '$id_evento' GROUP BY nome ORDER BY pontos DESC posicao ASC"); Não estou conseguindo acertar a consulta, alguém me ajuda?
×

Important Information

Ao usar o fórum, você concorda com nossos Terms of Use.