Functional programming is "programming with functions," where a function has some expected mathematical properties, including referential transparency. From these properties, further properties flow, in particular familiar reasoning steps enabled by substitutability that lead to mathematical proofs (i.e. justifying confidence in a result).
It follows that a functional program is merely an expression.
You can easily see the contrast between the two styles by noting the places in an imperative program where an expression is no longer referentially transparent (and therefore is not built with functions and values, and cannot itself be part of a function). The two most obvious places are: mutation (e.g. variables) other side-effects non-local control flow (e.g. exceptions)
On this framework of programs-as-expressions which are composed of functions and values, is built an entire practical paradigm of languages, concepts, "functional patterns", combinators, and various type systems and evaluation algorithms.
By the most extreme definition, almost any language—even C or Java—can be called functional, but usually people reserve the term for languages with specifically relevant abstractions (such as closures, immutable values, and syntactic aids like pattern matching). As far as use of functional programming is concerned it involves use of functins and builds code without any side effects . used to write proofs